+bool\r
+MatrixClientSetDeviceId(\r
+ MatrixClient * client,\r
+ const char * deviceId)\r
+{\r
+ for (int i = 0; i < DEVICE_ID_SIZE-1; i++)\r
+ client->deviceId[i] = deviceId[i];\r
+ client->deviceId[DEVICE_ID_SIZE-1] = '\0';\r
+\r
+ return true;\r
+}\r
+\r
+bool\r
+MatrixClientSetUserId(\r
+ MatrixClient * client,\r
+ const char * userId)\r
+{\r
+ for (int i = 0; i < USER_ID_SIZE-1; i++)\r
+ client->userId[i] = userId[i];\r
+ client->userId[USER_ID_SIZE-1] = '\0';\r
+\r
+ return true;\r
+}\r
+\r
+bool\r
+MatrixClientGenerateOnetimeKeys(\r
+ MatrixClient * client,\r
+ int numberOfKeys)\r
+{\r
+ static uint8_t random[OLM_ONETIME_KEYS_RANDOM_SIZE];\r
+ Randomize(random, OLM_ONETIME_KEYS_RANDOM_SIZE);\r
+\r
+ size_t res =\r
+ olm_account_generate_one_time_keys(client->olmAccount.account,\r
+ numberOfKeys, random, OLM_ONETIME_KEYS_RANDOM_SIZE);\r
+\r
+ return res != olm_error();\r
+}\r
+\r
+// https://spec.matrix.org/v1.7/client-server-api/#post_matrixclientv3keysupload\r
+bool\r
+MatrixClientUploadOnetimeKeys(\r
+ MatrixClient * client)\r
+{\r
+ static char requestBuffer[KEYS_UPLOAD_REQUEST_SIZE];\r
+\r
+ mjson_snprintf(requestBuffer, KEYS_UPLOAD_REQUEST_SIZE,\r
+ "{");\r
+\r
+ static char onetimeKeysBuffer[1024];\r
+ olm_account_one_time_keys(client->olmAccount.account,\r
+ onetimeKeysBuffer, 1024);\r
+\r
+ const char *keys;\r
+ int keysLen;\r
+ mjson_find(onetimeKeysBuffer, strlen(onetimeKeysBuffer), "$.curve25519", &keys, &keysLen);\r
+\r
+ int koff, klen, voff, vlen, vtype, off = 0;\r
+ while ((off = mjson_next(keys, keysLen, off, &koff, &klen, &voff, &vlen, &vtype)) != 0) {\r
+ static char keyJson[JSON_ONETIME_KEY_SIZE];\r
+ \r
+ int keyJsonLen =\r
+ snprintf(keyJson, JSON_ONETIME_KEY_SIZE,\r
+ "{\"key\":\"%.*s\"}",\r
+ vlen-2, keys + voff+1);\r
+\r
+ static char keyJsonSigned[JSON_ONETIME_KEY_SIGNED_SIZE];\r
+\r
+ JsonSign(client,\r
+ keyJson, keyJsonLen,\r
+ keyJsonSigned, JSON_ONETIME_KEY_SIGNED_SIZE);\r
+ \r
+ mjson_snprintf(requestBuffer+strlen(requestBuffer), KEYS_UPLOAD_REQUEST_SIZE-strlen(requestBuffer),\r
+ "\"signed_curve25519:%.*s\":%s,",\r
+ klen-2, keys + koff+1,\r
+ keyJsonSigned);\r
+ }\r
+\r
+ if (requestBuffer[strlen(requestBuffer)-1] == ',')\r
+ requestBuffer[strlen(requestBuffer)-1] = '\0';\r
+\r
+ mjson_snprintf(requestBuffer+strlen(requestBuffer), KEYS_UPLOAD_REQUEST_SIZE-strlen(requestBuffer),\r
+ "}");\r
+ \r
+ // static char onetimeKeysSignedBuffer[KEYS_UPLOAD_REQUEST_SIGNED_SIZE];\r
+ // JsonSign(client,\r
+ // requestBuffer, strlen(requestBuffer),\r
+ // onetimeKeysSignedBuffer, KEYS_UPLOAD_REQUEST_SIZE);\r
+ \r
+ // static char finalEvent[KEYS_UPLOAD_REQUEST_SIGNED_SIZE];\r
+ // snprintf(finalEvent, KEYS_UPLOAD_REQUEST_SIGNED_SIZE,\r
+ // "{\"one_time_keys\":%s}", onetimeKeysSignedBuffer);\r
+ static char finalEvent[KEYS_UPLOAD_REQUEST_SIGNED_SIZE];\r
+ snprintf(finalEvent, KEYS_UPLOAD_REQUEST_SIGNED_SIZE,\r
+ "{\"one_time_keys\":%s}", requestBuffer);\r
+\r
+ static char responseBuffer[KEYS_UPLOAD_RESPONSE_SIZE];\r
+ MatrixHttpPost(client,\r
+ KEYS_UPLOAD_URL,\r
+ finalEvent,\r
+ responseBuffer, KEYS_UPLOAD_RESPONSE_SIZE,\r
+ true);\r
+\r
+ printf("%s\n", responseBuffer);\r
+\r
+ return true;\r
+}\r
+\r
+// https://spec.matrix.org/v1.7/client-server-api/#post_matrixclientv3keysupload\r
+bool\r
+MatrixClientUploadDeviceKey(\r
+ MatrixClient * client)\r
+{\r
+ char thisDeviceKey[DEVICE_KEY_SIZE];\r
+ MatrixOlmAccountGetDeviceKey(&client->olmAccount, thisDeviceKey, DEVICE_KEY_SIZE);\r
+ char thisSigningKey[DEVICE_KEY_SIZE];\r
+ MatrixOlmAccountGetSigningKey(&client->olmAccount, thisSigningKey, DEVICE_KEY_SIZE);\r
+\r
+ static char deviceKeysBuffer[KEYS_UPLOAD_REQUEST_SIZE];\r
+\r
+ int deviceKeysBufferLen =\r
+ mjson_snprintf(deviceKeysBuffer, KEYS_UPLOAD_REQUEST_SIZE,\r
+ "{"\r
+ "\"algorithms\":[\"m.olm.v1.curve25519-aes-sha2\",\"m.megolm.v1.aes-sha2\"],"\r
+ "\"device_id\":\"%s\","\r
+ "\"keys\":{"\r
+ "\"curve25519:%s\":\"%s\","\r
+ "\"ed25519:%s\":\"%s\""\r
+ "},"\r
+ "\"user_id\":\"%s\""\r
+ "}",\r
+ client->deviceId,\r
+ client->deviceId, thisDeviceKey,\r
+ client->deviceId, thisSigningKey,\r
+ client->userId);\r
+\r
+ static char deviceKeysSignedBuffer[KEYS_UPLOAD_REQUEST_SIGNED_SIZE];\r
+ JsonSign(client,\r
+ deviceKeysBuffer, deviceKeysBufferLen,\r
+ deviceKeysSignedBuffer, KEYS_UPLOAD_REQUEST_SIZE);\r
+ \r
+ static char finalEvent[KEYS_UPLOAD_REQUEST_SIGNED_SIZE];\r
+ snprintf(finalEvent, KEYS_UPLOAD_REQUEST_SIGNED_SIZE,\r
+ "{\"device_keys\":%s}", deviceKeysSignedBuffer);\r
+\r
+ static char responseBuffer[KEYS_UPLOAD_RESPONSE_SIZE];\r
+ MatrixHttpPost(client,\r
+ KEYS_UPLOAD_URL,\r
+ finalEvent,\r
+ responseBuffer, KEYS_UPLOAD_RESPONSE_SIZE,\r
+ true);\r
+ \r
+ printf("%s\n", responseBuffer);\r