Skip to content

Commit

Permalink
Extra validation of returned XML
Browse files Browse the repository at this point in the history
  • Loading branch information
irtimmer committed Mar 21, 2016
1 parent 43c06a2 commit 016ac91
Showing 1 changed file with 111 additions and 5 deletions.
116 changes: 111 additions & 5 deletions libgamestream/client.c
Original file line number Diff line number Diff line change
Expand Up @@ -307,8 +307,26 @@ static int sign_it(const char *msg, size_t mlen, unsigned char **sig, size_t *sl
return result;
}

int gs_unpair(PSERVER_DATA server) {
char url[4096];
uuid_t uuid;
char uuid_str[37];
PHTTP_DATA data = http_create_data();
if (data == NULL)
return GS_OUT_OF_MEMORY;

uuid_generate_random(uuid);
uuid_unparse(uuid, uuid_str);
sprintf(url, "http://%s:47989/unpair?uniqueid=%s&uuid=%s", server->address, unique_id, uuid_str);
ret = http_request(url, data);

http_free_data(data);
return ret;
}

int gs_pair(PSERVER_DATA server, char* pin) {
int ret = GS_OK;
char* result = NULL;
char url[4096];
uuid_t uuid;
char uuid_str[37];
Expand Down Expand Up @@ -337,6 +355,15 @@ int gs_pair(PSERVER_DATA server, char* pin) {
else if ((ret = http_request(url, data)) != GS_OK)
goto cleanup;

if ((ret = xml_search(data->memory, data->size, "paired", &result)) != GS_OK)
goto cleanup;

if (strcmp(result, "1") != 0) {
gs_error = "Pairing failed";
ret = GS_FAILED;
goto cleanup;
}

unsigned char salt_pin[20];
unsigned char aes_key_hash[20];
AES_KEY enc_key, dec_key;
Expand All @@ -359,7 +386,19 @@ int gs_pair(PSERVER_DATA server, char* pin) {
if ((ret = http_request(url, data)) != GS_OK)
goto cleanup;

char *result;
free(result);
result = NULL;
if ((ret = xml_search(data->memory, data->size, "paired", &result)) != GS_OK)
goto cleanup;

if (strcmp(result, "1") != 0) {
gs_error = "Pairing failed";
ret = GS_FAILED;
goto cleanup;
}

free(result);
result = NULL;
if (xml_search(data->memory, data->size, "challengeresponse", &result) != GS_OK) {
ret = GS_INVALID;
goto cleanup;
Expand All @@ -370,7 +409,6 @@ int gs_pair(PSERVER_DATA server, char* pin) {
for (int count = 0; count < strlen(result); count += 2) {
sscanf(&result[count], "%2hhx", &challenge_response_data_enc[count / 2]);
}
free(result);

for (int i = 0; i < 48; i += 16) {
AES_decrypt(&challenge_response_data_enc[i], &challenge_response_data[i], &dec_key);
Expand Down Expand Up @@ -399,11 +437,26 @@ int gs_pair(PSERVER_DATA server, char* pin) {
if ((ret = http_request(url, data)) != GS_OK)
goto cleanup;

free(result);
result = NULL;
if ((ret = xml_search(data->memory, data->size, "paired", &result)) != GS_OK)
goto cleanup;

if (strcmp(result, "1") != 0) {
gs_error = "Pairing failed";
ret = GS_FAILED;
goto cleanup;
}

free(result);
result = NULL;
if (xml_search(data->memory, data->size, "pairingsecret", &result) != GS_OK) {
ret = GS_INVALID;
goto cleanup;
}

//TODO: verify pairingsecret

unsigned char *signature = NULL;
size_t s_len;
if (sign_it(client_secret_data, 16, &signature, &s_len, privateKey) != GS_OK) {
Expand All @@ -424,15 +477,40 @@ int gs_pair(PSERVER_DATA server, char* pin) {
if ((ret = http_request(url, data)) != GS_OK)
goto cleanup;

free(result);
result = NULL;
if ((ret = xml_search(data->memory, data->size, "paired", &result)) != GS_OK)
goto cleanup;

if (strcmp(result, "1") != 0) {
gs_error = "Pairing failed";
ret = GS_FAILED;
goto cleanup;
}

uuid_generate_random(uuid);
uuid_unparse(uuid, uuid_str);
sprintf(url, "https://%s:47984/pair?uniqueid=%s&uuid=%s&devicename=roth&updateState=1&phrase=pairchallenge", server->address, unique_id, uuid_str);
if ((ret = http_request(url, data)) != GS_OK)
goto cleanup;

free(result);
result = NULL;
if ((ret = xml_search(data->memory, data->size, "paired", &result)) != GS_OK)
goto cleanup;

if (strcmp(result, "1") != 0) {
gs_error = "Pairing failed";
ret = GS_FAILED;
goto cleanup;
}

server->paired = true;

cleanup:
if (result != NULL)
free(result);

http_free_data(data);

return ret;
Expand Down Expand Up @@ -461,6 +539,7 @@ int gs_applist(PSERVER_DATA server, PAPP_LIST *list) {

int gs_start_app(PSERVER_DATA server, STREAM_CONFIGURATION *config, int appId, bool sops, bool localaudio) {
uuid_t uuid;
char* result = NULL;
char uuid_str[37];

if (config->height >= 2160 && !server->supports4K)
Expand Down Expand Up @@ -488,9 +567,22 @@ int gs_start_app(PSERVER_DATA server, STREAM_CONFIGURATION *config, int appId, b
} else
sprintf(url, "https://%s:47984/resume?uniqueid=%s&uuid=%s&rikey=%s&rikeyid=%d", server->address, unique_id, uuid_str, rikey_hex, rikeyid);

int ret = http_request(url, data);
if (ret == GS_OK)
if ((ret = http_request(url, data)) == GS_OK)
server->currentGame = appId;
else
goto cleanup;

if ((ret = xml_search(data->memory, data->size, "cancel", &result)) != GS_OK)
goto cleanup;

if (atoi(result) == 0) {
ret = GS_FAILED;
goto cleanup;
}

cleanup:
if (result != NULL)
free(result);

http_free_data(data);
return ret;
Expand All @@ -500,14 +592,28 @@ int gs_quit_app(PSERVER_DATA server) {
char url[4096];
uuid_t uuid;
char uuid_str[37];
char* result = NULL;
PHTTP_DATA data = http_create_data();
if (data == NULL)
return GS_OUT_OF_MEMORY;

uuid_generate_random(uuid);
uuid_unparse(uuid, uuid_str);
sprintf(url, "https://%s:47984/cancel?uniqueid=%s&uuid=%s", server->address, unique_id, uuid_str);
int ret = http_request(url, data);
if ((ret = http_request(url, data)) != GS_OK)
goto cleanup;

if ((ret = xml_search(data->memory, data->size, "cancel", &result)) != GS_OK)

This comment has been minimized.

Copy link
@dead

dead Mar 29, 2016

Contributor

This is not working.

goto cleanup;

if (strcmp(result, "0") == 0) {
ret = GS_FAILED;
goto cleanup;
}

cleanup:
if (result != NULL)
free(result);

http_free_data(data);
return ret;
Expand Down

1 comment on commit 016ac91

@cgutman
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like you forgot to declare ret in a few of these functions

/home/cgutman/moonlight-embedded/libgamestream/client.c: In function ‘gs_unpair’:
/home/cgutman/moonlight-embedded/libgamestream/client.c:321:3: error: ‘ret’ undeclared (first use in this function)
ret = http_request(url, data);
^
/home/cgutman/moonlight-embedded/libgamestream/client.c:321:3: note: each undeclared identifier is reported only once for each function it appears in
/home/cgutman/moonlight-embedded/libgamestream/client.c: In function ‘gs_start_app’:
/home/cgutman/moonlight-embedded/libgamestream/client.c:570:8: error: ‘ret’ undeclared (first use in this function)
if ((ret = http_request(url, data)) == GS_OK)
^
/home/cgutman/moonlight-embedded/libgamestream/client.c: In function ‘gs_quit_app’:
/home/cgutman/moonlight-embedded/libgamestream/client.c:603:8: error: ‘ret’ undeclared (first use in this function)
if ((ret = http_request(url, data)) != GS_OK)

Please sign in to comment.