in src/source/Common/Lws/LwsCall.c [7:97]
STATUS blockingLwsCall(PRequestInfo pRequestInfo, PCallInfo pCallInfo)
{
ENTERS();
STATUS retStatus = STATUS_SUCCESS;
PCHAR pHostStart, pHostEnd;
CHAR path[MAX_URI_CHAR_LEN + 1];
struct lws_context* lwsContext = NULL;
struct lws_context_creation_info creationInfo;
struct lws_client_connect_info connectInfo;
struct lws* clientLws = NULL;
volatile INT32 retVal = 0;
struct lws_protocols lwsProtocols[2];
CHK(pRequestInfo != NULL && pCallInfo != NULL, STATUS_NULL_ARG);
// Prepare the signaling channel protocols array
MEMSET(lwsProtocols, 0x00, SIZEOF(lwsProtocols));
lwsProtocols[0].name = HTTPS_SCHEME_NAME;
lwsProtocols[0].callback = lwsIotCallbackRoutine;
lwsProtocols[1].name = NULL;
lwsProtocols[1].callback = NULL;
// Prepare the LWS context
MEMSET(&creationInfo, 0x00, SIZEOF(struct lws_context_creation_info));
creationInfo.options = LWS_SERVER_OPTION_DO_SSL_GLOBAL_INIT;
creationInfo.port = CONTEXT_PORT_NO_LISTEN;
creationInfo.protocols = lwsProtocols;
creationInfo.timeout_secs = pRequestInfo->completionTimeout / HUNDREDS_OF_NANOS_IN_A_SECOND;
creationInfo.gid = -1;
creationInfo.uid = -1;
creationInfo.fd_limit_per_thread = 1 + 1 + 1;
creationInfo.client_ssl_ca_filepath = pRequestInfo->certPath;
creationInfo.client_ssl_cert_filepath = pRequestInfo->sslCertPath;
creationInfo.client_ssl_private_key_filepath = pRequestInfo->sslPrivateKeyPath;
CHK(NULL != (lwsContext = lws_create_context(&creationInfo)), STATUS_IOT_CREATE_LWS_CONTEXT_FAILED);
// Execute the LWS REST call
MEMSET(&connectInfo, 0x00, SIZEOF(struct lws_client_connect_info));
connectInfo.context = lwsContext;
connectInfo.ssl_connection = LCCSCF_USE_SSL;
connectInfo.port = DEFAULT_SSL_PORT_NUMBER;
CHK_STATUS(getRequestHost(pRequestInfo->url, &pHostStart, &pHostEnd));
// Store the path
STRNCPY(path, pHostEnd, MAX_URI_CHAR_LEN);
path[MAX_URI_CHAR_LEN] = '\0';
// NULL terminate the host
*pHostEnd = '\0';
connectInfo.address = pHostStart;
connectInfo.path = path;
connectInfo.host = connectInfo.address;
connectInfo.method = HTTP_REQUEST_VERB_GET_STRING;
connectInfo.protocol = lwsProtocols[0].name;
connectInfo.pwsi = &clientLws;
connectInfo.opaque_user_data = (PVOID) pCallInfo;
CHK(NULL != lws_client_connect_via_info(&connectInfo), STATUS_IOT_CREATE_LWS_CONTEXT_FAILED);
while (retVal >= 0 && !ATOMIC_LOAD_BOOL(&pCallInfo->pRequestInfo->terminating)) {
retVal = lws_service(lwsContext, 0);
}
CleanUp:
if(retStatus == STATUS_IOT_CREATE_LWS_CONTEXT_FAILED)
{
DLOGW("Unable to create LWS context or connect to Websocket server");
}
else
{
CHK_LOG_ERR(retStatus);
}
if (lwsContext != NULL) {
// Trigger termination
ATOMIC_STORE_BOOL(&pCallInfo->pRequestInfo->terminating, TRUE);
// Cancel the ongoing service if any
lws_cancel_service(lwsContext);
// Destroy the context
lws_context_destroy(lwsContext);
}
LEAVES();
return retStatus;
}