Merge commit '227425b90e9a671118026689dd30967e127a1090' as 'external/toxcore/c-toxcore'
This commit is contained in:
101
external/toxcore/c-toxcore/other/fun/BUILD.bazel
vendored
Normal file
101
external/toxcore/c-toxcore/other/fun/BUILD.bazel
vendored
Normal file
@ -0,0 +1,101 @@
|
||||
load("@rules_cc//cc:defs.bzl", "cc_binary")
|
||||
|
||||
package(features = ["layering_check"])
|
||||
|
||||
#cc_binary(
|
||||
# name = "cracker",
|
||||
# testonly = 1,
|
||||
# srcs = ["cracker.c"],
|
||||
# copts = ["-fopenmp"],
|
||||
# linkopts = ["-fopenmp"],
|
||||
# deps = [
|
||||
# "//c-toxcore/toxcore:ccompat",
|
||||
# "@libsodium",
|
||||
# ],
|
||||
#)
|
||||
|
||||
cc_binary(
|
||||
name = "cracker_simple",
|
||||
testonly = 1,
|
||||
srcs = ["cracker_simple.c"],
|
||||
deps = [
|
||||
"//c-toxcore/testing:misc_tools",
|
||||
"//c-toxcore/toxcore:ccompat",
|
||||
"@libsodium",
|
||||
],
|
||||
)
|
||||
|
||||
cc_binary(
|
||||
name = "create_minimal_savedata",
|
||||
testonly = 1,
|
||||
srcs = [
|
||||
"create_common.h",
|
||||
"create_minimal_savedata.c",
|
||||
],
|
||||
deps = [
|
||||
"//c-toxcore/toxcore:ccompat",
|
||||
"@libsodium",
|
||||
],
|
||||
)
|
||||
|
||||
cc_binary(
|
||||
name = "create_savedata",
|
||||
testonly = 1,
|
||||
srcs = [
|
||||
"create_common.h",
|
||||
"create_savedata.c",
|
||||
],
|
||||
deps = [
|
||||
"//c-toxcore/toxcore:ccompat",
|
||||
"//c-toxcore/toxcore:tox",
|
||||
"@libsodium",
|
||||
],
|
||||
)
|
||||
|
||||
cc_binary(
|
||||
name = "create_bootstrap_keys",
|
||||
testonly = 1,
|
||||
srcs = [
|
||||
"create_bootstrap_keys.c",
|
||||
"create_common.h",
|
||||
],
|
||||
deps = [
|
||||
"//c-toxcore/toxcore:ccompat",
|
||||
"@libsodium",
|
||||
],
|
||||
)
|
||||
|
||||
cc_binary(
|
||||
name = "sign",
|
||||
testonly = 1,
|
||||
srcs = ["sign.c"],
|
||||
copts = ["-w"],
|
||||
deps = [
|
||||
"//c-toxcore/testing:misc_tools",
|
||||
"//c-toxcore/toxcore:ccompat",
|
||||
"@libsodium",
|
||||
],
|
||||
)
|
||||
|
||||
cc_binary(
|
||||
name = "strkey",
|
||||
testonly = 1,
|
||||
srcs = ["strkey.c"],
|
||||
copts = ["-w"],
|
||||
deps = [
|
||||
"//c-toxcore/toxcore:ccompat",
|
||||
"//c-toxcore/toxcore:tox",
|
||||
"@libsodium",
|
||||
],
|
||||
)
|
||||
|
||||
cc_binary(
|
||||
name = "save-generator",
|
||||
testonly = 1,
|
||||
srcs = ["save-generator.c"],
|
||||
deps = [
|
||||
"//c-toxcore/testing:misc_tools",
|
||||
"//c-toxcore/toxcore:ccompat",
|
||||
"//c-toxcore/toxcore:tox",
|
||||
],
|
||||
)
|
30
external/toxcore/c-toxcore/other/fun/CMakeLists.txt
vendored
Normal file
30
external/toxcore/c-toxcore/other/fun/CMakeLists.txt
vendored
Normal file
@ -0,0 +1,30 @@
|
||||
add_executable(save-generator save-generator.c)
|
||||
target_link_modules(save-generator toxcore misc_tools)
|
||||
|
||||
add_executable(strkey strkey.c)
|
||||
target_link_modules(strkey toxcore ${LIBSODIUM_LIBRARIES})
|
||||
|
||||
add_executable(create_bootstrap_keys create_bootstrap_keys.c)
|
||||
target_link_modules(create_bootstrap_keys ${LIBSODIUM_LIBRARIES})
|
||||
|
||||
add_executable(create_minimal_savedata create_minimal_savedata.c)
|
||||
target_link_modules(create_minimal_savedata ${LIBSODIUM_LIBRARIES})
|
||||
|
||||
add_executable(create_savedata create_savedata.c)
|
||||
target_link_modules(create_savedata toxcore ${LIBSODIUM_LIBRARIES})
|
||||
|
||||
add_executable(sign sign.c)
|
||||
target_link_modules(sign ${LIBSODIUM_LIBRARIES} misc_tools)
|
||||
|
||||
add_executable(cracker_simple cracker_simple.c)
|
||||
target_link_modules(cracker_simple ${LIBSODIUM_LIBRARIES} misc_tools)
|
||||
|
||||
# MSVC doesn't support OpenMP
|
||||
if(NOT MSVC)
|
||||
find_package(OpenMP)
|
||||
if(OpenMP_C_FOUND)
|
||||
add_executable(cracker cracker.c)
|
||||
target_link_modules(cracker ${LIBSODIUM_LIBRARIES})
|
||||
target_link_libraries(cracker OpenMP::OpenMP_C)
|
||||
endif()
|
||||
endif()
|
122
external/toxcore/c-toxcore/other/fun/bootstrap_node_info.py
vendored
Executable file
122
external/toxcore/c-toxcore/other/fun/bootstrap_node_info.py
vendored
Executable file
@ -0,0 +1,122 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
Copyright (c) 2014 by nurupo <nurupo.contributions@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
"""
|
||||
import socket
|
||||
import sys
|
||||
|
||||
if sys.version_info[0] == 2:
|
||||
print("This script requires Python 3+ in order to run.")
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
def print_help(prog: str) -> None:
|
||||
"""Print program usage to stdout."""
|
||||
print(f"Usage: {prog} <ipv4|ipv6> <ip/hostname> <port>")
|
||||
print(f" Example: {prog} ipv4 192.210.149.121 33445")
|
||||
print(f" Example: {prog} ipv4 23.226.230.47 33445")
|
||||
print(f" Example: {prog} ipv4 node.tox.biribiri.org 33445")
|
||||
print(f" Example: {prog} ipv4 cerberus.zodiaclabs.org 33445")
|
||||
print(f" Example: {prog} ipv6 2604:180:1::3ded:b280 33445")
|
||||
print("")
|
||||
print("Return values:")
|
||||
print(" 0 - received info reply from a node")
|
||||
print(" 1 - incorrect command line arguments")
|
||||
print(" 2 - didn't receive any reply from a node")
|
||||
print(" 3 - received a malformed/unexpected reply")
|
||||
|
||||
|
||||
# https://github.com/irungentoo/toxcore/blob/4940c4c62b6014d1f0586aa6aca7bf6e4ecfcf29/toxcore/network.h#L128
|
||||
INFO_PACKET_ID = b"\xF0"
|
||||
# https://github.com/irungentoo/toxcore/blob/881b2d900d1998981fb6b9938ec66012d049635f/other/bootstrap_node_packets.c#L28
|
||||
INFO_REQUEST_PACKET_LENGTH = 78
|
||||
# first byte is INFO_REQUEST_ID, other bytes don't matter as long as reqest's
|
||||
# length matches INFO_REQUEST_LENGTH
|
||||
INFO_REQUEST_PACKET = INFO_PACKET_ID + (
|
||||
b"0" * (INFO_REQUEST_PACKET_LENGTH - len(INFO_PACKET_ID)))
|
||||
|
||||
PACKET_ID_LENGTH = len(INFO_PACKET_ID)
|
||||
# https://github.com/irungentoo/toxcore/blob/881b2d900d1998981fb6b9938ec66012d049635f/other/bootstrap_node_packets.c#L44
|
||||
VERSION_LENGTH = 4
|
||||
# https://github.com/irungentoo/toxcore/blob/881b2d900d1998981fb6b9938ec66012d049635f/other/bootstrap_node_packets.c#L26
|
||||
MAX_MOTD_LENGTH = 256
|
||||
|
||||
MAX_INFO_RESPONSE_PACKET_LENGTH = PACKET_ID_LENGTH + VERSION_LENGTH + MAX_MOTD_LENGTH
|
||||
|
||||
SOCK_TIMEOUT_SECONDS = 1.0
|
||||
|
||||
|
||||
def main(prog: str, protocol: str, host: str, port: int) -> None:
|
||||
"""Call the bootstrap node info RPC and output the response."""
|
||||
if protocol == "ipv4":
|
||||
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
|
||||
elif protocol == "ipv6":
|
||||
sock = socket.socket(socket.AF_INET6, socket.SOCK_DGRAM)
|
||||
else:
|
||||
print("Invalid first argument")
|
||||
print_help(prog)
|
||||
sys.exit(1)
|
||||
|
||||
sock.sendto(INFO_REQUEST_PACKET, (host, port))
|
||||
|
||||
sock.settimeout(SOCK_TIMEOUT_SECONDS)
|
||||
|
||||
try:
|
||||
data, _ = sock.recvfrom(MAX_INFO_RESPONSE_PACKET_LENGTH)
|
||||
except socket.timeout:
|
||||
print("The DHT bootstrap node didn't reply in " +
|
||||
str(SOCK_TIMEOUT_SECONDS) + " sec.")
|
||||
print("The likely reason for that is that the DHT bootstrap node "
|
||||
"is either offline or has no info set.")
|
||||
sys.exit(2)
|
||||
|
||||
packet_id = data[:PACKET_ID_LENGTH]
|
||||
if packet_id != INFO_PACKET_ID:
|
||||
print("Bad response, first byte should be {info_packet_id!r}"
|
||||
" but got {packet_id!r}({data!r})".format(
|
||||
info_packet_id=INFO_PACKET_ID,
|
||||
packet_id=packet_id,
|
||||
data=data,
|
||||
))
|
||||
print("Are you sure that you are pointing the script at a Tox "
|
||||
"DHT bootstrap node and that the script is up to date?")
|
||||
sys.exit(3)
|
||||
|
||||
version = int.from_bytes(data[PACKET_ID_LENGTH:PACKET_ID_LENGTH +
|
||||
VERSION_LENGTH],
|
||||
byteorder="big")
|
||||
motd = data[PACKET_ID_LENGTH + VERSION_LENGTH:].decode("utf-8")
|
||||
print("Version: " + str(version))
|
||||
print("MOTD: " + motd)
|
||||
sys.exit(0)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
if len(sys.argv) != 4:
|
||||
print_help(sys.argv[0])
|
||||
sys.exit(1)
|
||||
|
||||
main(
|
||||
prog=sys.argv[0],
|
||||
protocol=sys.argv[1],
|
||||
host=sys.argv[2],
|
||||
port=int(sys.argv[3]),
|
||||
)
|
255
external/toxcore/c-toxcore/other/fun/cracker.c
vendored
Normal file
255
external/toxcore/c-toxcore/other/fun/cracker.c
vendored
Normal file
@ -0,0 +1,255 @@
|
||||
/* Public key cracker.
|
||||
*
|
||||
* Can be used to find public keys starting with specific hex (ABCD) for example.
|
||||
*
|
||||
* NOTE: There's probably a way to make this faster.
|
||||
*
|
||||
* Usage: ./cracker ABCDEF
|
||||
*
|
||||
* Will try to find a public key starting with: ABCDEF
|
||||
*/
|
||||
|
||||
#include <inttypes.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
|
||||
/* Sodium includes*/
|
||||
#include <sodium/crypto_scalarmult_curve25519.h>
|
||||
#include <sodium/randombytes.h>
|
||||
|
||||
/* NULL compatibility macro */
|
||||
#include "../../toxcore/ccompat.h"
|
||||
|
||||
#define KEY_LEN 32
|
||||
// Maximum number of bytes this program can crack in one run
|
||||
#define MAX_CRACK_BYTES 8
|
||||
// Maximum length of hex encoded prefix
|
||||
#define MAX_HEX_PREFIX_LEN (MAX_CRACK_BYTES * 2)
|
||||
|
||||
#if defined(_OPENMP)
|
||||
#include <omp.h>
|
||||
#define NUM_THREADS() ((unsigned) omp_get_max_threads())
|
||||
#else
|
||||
#define NUM_THREADS() (1U)
|
||||
#endif
|
||||
|
||||
static void print_key(const uint8_t *client_id)
|
||||
{
|
||||
for (uint32_t j = 0; j < 32; ++j) {
|
||||
printf("%02X", client_id[j]);
|
||||
}
|
||||
}
|
||||
|
||||
/// bytes needs to be at least (hex_len+1)/2 long
|
||||
static size_t hex_string_to_bin(const char *hex_string, size_t hex_len, uint8_t *bytes)
|
||||
{
|
||||
size_t i;
|
||||
const char *pos = hex_string;
|
||||
// make even
|
||||
|
||||
for (i = 0; i < hex_len / 2; ++i, pos += 2) {
|
||||
uint8_t val;
|
||||
|
||||
if (sscanf(pos, "%02hhx", &val) != 1) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
bytes[i] = val;
|
||||
}
|
||||
|
||||
if (i * 2 < hex_len) {
|
||||
uint8_t val;
|
||||
|
||||
if (sscanf(pos, "%hhx", &val) != 1) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
bytes[i] = (uint8_t)(val << 4);
|
||||
++i;
|
||||
}
|
||||
|
||||
return i;
|
||||
}
|
||||
|
||||
static size_t match_hex_prefix(const uint8_t *key, const uint8_t *prefix, size_t prefix_len)
|
||||
{
|
||||
size_t same = 0;
|
||||
uint8_t diff = 0;
|
||||
size_t i;
|
||||
|
||||
for (i = 0; i < prefix_len / 2; ++i) {
|
||||
diff = key[i] ^ prefix[i];
|
||||
|
||||
// First check high nibble
|
||||
if ((diff & 0xF0) == 0) {
|
||||
++same;
|
||||
}
|
||||
|
||||
// Then low nibble
|
||||
if (diff == 0) {
|
||||
++same;
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// check last high nibble
|
||||
if ((prefix_len % 2) && diff == 0) {
|
||||
diff = key[i] ^ prefix[i];
|
||||
|
||||
// First check high nibble
|
||||
if ((diff & 0xF0) == 0) {
|
||||
++same;
|
||||
}
|
||||
}
|
||||
|
||||
return same;
|
||||
}
|
||||
|
||||
static void cracker_core(uint64_t range_start, uint64_t range_end, uint64_t range_offs, uint64_t priv_key_shadow[4],
|
||||
uint32_t *longest_match, uint8_t hex_prefix[MAX_CRACK_BYTES], size_t prefix_chars_len)
|
||||
{
|
||||
#pragma omp parallel for firstprivate(priv_key_shadow) shared(longest_match, range_start, range_end, range_offs, hex_prefix, prefix_chars_len) schedule(static) default(none)
|
||||
|
||||
for (uint64_t batch = range_start; batch < range_end; ++batch) {
|
||||
uint8_t *priv_key = (uint8_t *) priv_key_shadow;
|
||||
/*
|
||||
* We can't use the first and last bytes because they are masked in
|
||||
* curve25519. Offset by 16 bytes to get better alignment.
|
||||
*/
|
||||
uint64_t *counter = priv_key_shadow + 2;
|
||||
/*
|
||||
* Add to `counter` instead of assign here, to preservere more randomness on short runs
|
||||
* There can be an intentional overflow in `batch + range_offs`
|
||||
*/
|
||||
*counter += batch + range_offs;
|
||||
uint8_t pub_key[KEY_LEN] = {0};
|
||||
|
||||
crypto_scalarmult_curve25519_base(pub_key, priv_key);
|
||||
|
||||
const unsigned matching = (unsigned) match_hex_prefix(pub_key, hex_prefix, prefix_chars_len);
|
||||
|
||||
// Global compare and update
|
||||
uint32_t l_longest_match;
|
||||
#pragma omp atomic read
|
||||
l_longest_match = *longest_match;
|
||||
|
||||
if (matching > l_longest_match) {
|
||||
#pragma omp atomic write
|
||||
*longest_match = matching;
|
||||
|
||||
#pragma omp critical
|
||||
{
|
||||
printf("%u chars matching: \n", matching);
|
||||
printf("Public key: ");
|
||||
print_key(pub_key);
|
||||
printf("\nSecret key: ");
|
||||
print_key(priv_key);
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void print_stats(double seconds_passed, double keys_tried)
|
||||
{
|
||||
printf("Runtime: %10lus, Keys tried %e/%e, Calculating %e keys/s\n",
|
||||
(unsigned long) seconds_passed, keys_tried, (double) UINT64_MAX, keys_tried / seconds_passed);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
if (argc < 2) {
|
||||
printf("usage: ./cracker public_key(or beginning of one in hex format)\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
const size_t prefix_chars_len = strlen(argv[1]);
|
||||
|
||||
/*
|
||||
* If you can afford the hardware to crack longer prefixes, you can probably
|
||||
* afford to rewrite this program.
|
||||
*/
|
||||
if (prefix_chars_len > MAX_HEX_PREFIX_LEN) {
|
||||
printf("Finding a key with more than 16 hex chars as prefix is not supported\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
uint8_t hex_prefix[MAX_CRACK_BYTES] = {0};
|
||||
|
||||
const size_t prefix_len = hex_string_to_bin(argv[1], prefix_chars_len, hex_prefix);
|
||||
|
||||
if (prefix_len == 0) {
|
||||
printf("Invalid hex key specified\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
printf("Searching for key with prefix: %s\n", argv[1]);
|
||||
|
||||
time_t start_time = time(nullptr);
|
||||
|
||||
// Declare private key bytes as uint64_t[4] so we can lower the alignment without problems
|
||||
uint64_t priv_key_shadow[KEY_LEN / 8];
|
||||
uint8_t *priv_key = (uint8_t *) priv_key_shadow;
|
||||
// Put randomness into the key
|
||||
randombytes(priv_key, KEY_LEN);
|
||||
uint32_t longest_match = 0;
|
||||
|
||||
|
||||
// Finishes a batch every ~10s on my PC
|
||||
const uint64_t batch_size = (UINT64_C(1) << 18) * NUM_THREADS();
|
||||
|
||||
// calculate remaining batch that doesn't fit the main loop
|
||||
const uint64_t rem_batch_size = UINT64_MAX % batch_size;
|
||||
|
||||
const uint64_t rem_start = UINT64_MAX - rem_batch_size - 1;
|
||||
|
||||
cracker_core(rem_start, UINT64_MAX, 1, priv_key_shadow, &longest_match, hex_prefix, prefix_chars_len);
|
||||
|
||||
double seconds_passed = difftime(time(nullptr), start_time);
|
||||
double old_seconds_passed = seconds_passed;
|
||||
|
||||
// Reduce time to first stats output
|
||||
print_stats(seconds_passed, rem_batch_size + 1);
|
||||
|
||||
if (longest_match >= prefix_chars_len) {
|
||||
printf("Found matching prefix, exiting...\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
for (uint64_t tries = 0; tries < rem_start; tries += batch_size) {
|
||||
cracker_core(tries, tries + batch_size, 0, priv_key_shadow, &longest_match, hex_prefix, prefix_chars_len);
|
||||
|
||||
seconds_passed = difftime(time(nullptr), start_time);
|
||||
// Use double type to avoid overflow in addition, we don't need precision here anyway
|
||||
double keys_tried = ((double) tries) + rem_batch_size + 1;
|
||||
|
||||
if (longest_match >= prefix_chars_len) {
|
||||
print_stats(seconds_passed, keys_tried);
|
||||
printf("Found matching prefix, exiting...\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Rate limit output
|
||||
if (seconds_passed - old_seconds_passed > 5.0) {
|
||||
old_seconds_passed = seconds_passed;
|
||||
print_stats(seconds_passed, keys_tried);
|
||||
fflush(stdout);
|
||||
}
|
||||
}
|
||||
|
||||
printf("Congrats future person who successfully searched a key space of 2^64\n");
|
||||
uint64_t *counter = priv_key_shadow + 2;
|
||||
*counter = 0;
|
||||
printf("Didn't find anything from:\n");
|
||||
print_key(priv_key);
|
||||
printf("\nto:\n");
|
||||
*counter = UINT64_MAX;
|
||||
print_key(priv_key);
|
||||
printf("\n");
|
||||
return 2;
|
||||
}
|
84
external/toxcore/c-toxcore/other/fun/cracker_simple.c
vendored
Normal file
84
external/toxcore/c-toxcore/other/fun/cracker_simple.c
vendored
Normal file
@ -0,0 +1,84 @@
|
||||
/* Public key cracker.
|
||||
*
|
||||
* Can be used to find public keys starting with specific hex (ABCD) for example.
|
||||
*
|
||||
* NOTE: There's probably a way to make this faster.
|
||||
*
|
||||
* Usage: ./cracker ABCDEF
|
||||
*
|
||||
* Will try to find a public key starting with: ABCDEF
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
/* Sodium includes*/
|
||||
#include <sodium/crypto_scalarmult_curve25519.h>
|
||||
#include <sodium/randombytes.h>
|
||||
|
||||
#include "../../testing/misc_tools.h"
|
||||
#include "../../toxcore/ccompat.h"
|
||||
|
||||
// Secret key and public key length
|
||||
#define KEY_LEN 32
|
||||
|
||||
static void print_key(const uint8_t *client_id)
|
||||
{
|
||||
for (int j = 0; j < KEY_LEN; ++j) {
|
||||
printf("%02X", client_id[j]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
if (argc < 2) {
|
||||
printf("usage: ./cracker public_key(or beginning of one in hex format)\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
long long unsigned int num_tries = 0;
|
||||
|
||||
size_t len = strlen(argv[1]) / 2;
|
||||
unsigned char *key = hex_string_to_bin(argv[1]);
|
||||
uint8_t pub_key[KEY_LEN], priv_key[KEY_LEN], c_key[KEY_LEN];
|
||||
|
||||
if (len > KEY_LEN) {
|
||||
printf("%zu characters given, truncating to: %d\n", len * 2, KEY_LEN * 2);
|
||||
len = KEY_LEN;
|
||||
}
|
||||
|
||||
memcpy(c_key, key, len);
|
||||
free(key);
|
||||
randombytes(priv_key, KEY_LEN);
|
||||
|
||||
while (1) {
|
||||
crypto_scalarmult_curve25519_base(pub_key, priv_key);
|
||||
|
||||
if (memcmp(c_key, pub_key, len) == 0) {
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* We can't use the first and last bytes because they are masked in
|
||||
* curve25519. Using them would generate duplicate keys.
|
||||
*/
|
||||
for (int i = (KEY_LEN - 1); i > 1; --i) {
|
||||
priv_key[i - 1] += 1;
|
||||
|
||||
if (priv_key[i - 1] != 0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
++num_tries;
|
||||
}
|
||||
|
||||
printf("Public key:\n");
|
||||
print_key(pub_key);
|
||||
printf("\nPrivate key:\n");
|
||||
print_key(priv_key);
|
||||
printf("\n %llu keys tried\n", num_tries);
|
||||
return 0;
|
||||
}
|
28
external/toxcore/c-toxcore/other/fun/create_bootstrap_keys.c
vendored
Normal file
28
external/toxcore/c-toxcore/other/fun/create_bootstrap_keys.c
vendored
Normal file
@ -0,0 +1,28 @@
|
||||
/* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*
|
||||
* Creates bootstrap keys data for a given secret key, if provided, or a random key otherwise.
|
||||
* The data is written to stderr, human-readable key info is written to stdout.
|
||||
*
|
||||
* Build: gcc -o create_bootstrap_keys create_bootstrap_key.c -lsodium -std=c99
|
||||
*
|
||||
* Usage: ./create_bootstrap_key [secret-key] 2>data
|
||||
*/
|
||||
#include <stdio.h>
|
||||
|
||||
#include "create_common.h"
|
||||
|
||||
int main(const int argc, const char *const argv[])
|
||||
{
|
||||
init_sodium();
|
||||
|
||||
unsigned char public_key[crypto_box_PUBLICKEYBYTES];
|
||||
unsigned char secret_key[crypto_box_SECRETKEYBYTES];
|
||||
handle_args(argc, argv, "Creates bootstrap keys data", public_key, secret_key);
|
||||
|
||||
print_keys(public_key, secret_key);
|
||||
|
||||
fwrite(public_key, sizeof(public_key), 1, stderr);
|
||||
fwrite(secret_key, sizeof(secret_key), 1, stderr);
|
||||
|
||||
return 0;
|
||||
}
|
89
external/toxcore/c-toxcore/other/fun/create_common.h
vendored
Normal file
89
external/toxcore/c-toxcore/other/fun/create_common.h
vendored
Normal file
@ -0,0 +1,89 @@
|
||||
/* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*
|
||||
* Shared functions of create_*.c programs.
|
||||
*/
|
||||
#include <ctype.h>
|
||||
#include <stdbool.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <sodium.h>
|
||||
|
||||
#include "../../toxcore/ccompat.h"
|
||||
|
||||
static void init_sodium(void)
|
||||
{
|
||||
if (sodium_init() < 0) {
|
||||
printf("Error: Failed to initialize sodium.\n");
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
static int tox_strcasecmp(const char *s1, const char *s2)
|
||||
{
|
||||
while (true) {
|
||||
const int c1 = tolower(*(s1++));
|
||||
const int c2 = tolower(*(s2++));
|
||||
|
||||
if (c1 == '\0' || c2 == '\0' || c1 != c2) {
|
||||
return c1 - c2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void print_usage(const char *const argv0, const char *const does_what)
|
||||
{
|
||||
printf("%s for a given secret key, if provided, or a random key otherwise.\n", does_what);
|
||||
printf("The data is written to stderr, human-readable key info is written to stdout.\n");
|
||||
printf("\nUsage: %s [secret-key] 2>data\n", argv0);
|
||||
}
|
||||
|
||||
static void handle_args(const int argc, const char *const argv[], const char *const does_what,
|
||||
unsigned char *const public_key, unsigned char *const secret_key)
|
||||
{
|
||||
if (argc == 2 && (!tox_strcasecmp(argv[1], "-h") || !tox_strcasecmp(argv[1], "--help"))) {
|
||||
print_usage(argv[0], does_what);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
if (argc == 1) {
|
||||
crypto_box_keypair(public_key, secret_key);
|
||||
} else if (argc == 2 && strlen(argv[1]) == crypto_box_SECRETKEYBYTES * 2) {
|
||||
size_t bin_len = 0;
|
||||
|
||||
if (sodium_hex2bin(secret_key, crypto_box_SECRETKEYBYTES, argv[1], crypto_box_SECRETKEYBYTES * 2, nullptr, &bin_len,
|
||||
nullptr) != 0 || bin_len != crypto_box_SECRETKEYBYTES) {
|
||||
printf("Error: Secret key must be a hex string.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
crypto_scalarmult_base(public_key, secret_key);
|
||||
} else if (argc == 2) {
|
||||
printf("Error: Secret key must be a %u character hex string.\n", crypto_box_SECRETKEYBYTES * 2);
|
||||
exit(1);
|
||||
} else {
|
||||
print_usage(argv[0], does_what);
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
static void bin2hex_toupper(char *const hex, const size_t hex_maxlen, const unsigned char *const bin,
|
||||
const size_t bin_len)
|
||||
{
|
||||
sodium_bin2hex(hex, hex_maxlen, bin, bin_len);
|
||||
|
||||
for (size_t i = 0; i < hex_maxlen; i ++) {
|
||||
hex[i] = (char)toupper(hex[i]);
|
||||
}
|
||||
}
|
||||
|
||||
static void print_keys(const unsigned char *const public_key, const unsigned char *const secret_key)
|
||||
{
|
||||
char public_key_str[crypto_box_PUBLICKEYBYTES * 2 + 1];
|
||||
char secret_key_str[crypto_box_SECRETKEYBYTES * 2 + 1];
|
||||
bin2hex_toupper(public_key_str, sizeof(public_key_str), public_key, crypto_box_PUBLICKEYBYTES);
|
||||
bin2hex_toupper(secret_key_str, sizeof(secret_key_str), secret_key, crypto_box_SECRETKEYBYTES);
|
||||
fprintf(stdout, "Public key: %s\n", public_key_str);
|
||||
fprintf(stdout, "Secret key: %s\n", secret_key_str);
|
||||
}
|
58
external/toxcore/c-toxcore/other/fun/create_minimal_savedata.c
vendored
Normal file
58
external/toxcore/c-toxcore/other/fun/create_minimal_savedata.c
vendored
Normal file
@ -0,0 +1,58 @@
|
||||
/* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*
|
||||
* Creates minimal Tox savedata for a given secret key, if provided, or a random key otherwise.
|
||||
* The data is written to stderr, human-readable key info is written to stdout.
|
||||
*
|
||||
* Build: gcc -o create_minimal_savedata create_minimal_savedata.c -lsodium -std=c99
|
||||
*
|
||||
* Usage: ./create_minimal_savedata [secret-key] 2>data
|
||||
*/
|
||||
#include <stdio.h>
|
||||
|
||||
#include <sodium.h>
|
||||
|
||||
#include "create_common.h"
|
||||
|
||||
int main(const int argc, const char *const argv[])
|
||||
{
|
||||
init_sodium();
|
||||
|
||||
unsigned char public_key[crypto_box_PUBLICKEYBYTES];
|
||||
unsigned char secret_key[crypto_box_SECRETKEYBYTES];
|
||||
handle_args(argc, argv, "Creates minimal Tox savedata", public_key, secret_key);
|
||||
|
||||
print_keys(public_key, secret_key);
|
||||
|
||||
// toxcore stores integers in savedata explicitly in little-endian, so this is indeed portable across architectures
|
||||
// 0x00000000 = (uint32_t) 0
|
||||
// 0x15ed1b1f = (uint32_t) STATE_COOKIE_GLOBAL
|
||||
// 0x00000044 = (uint32_t) (crypto_box_PUBLICKEYBYTES+crypto_box_SECRETKEYBYTES+sizeof(uint32_t))
|
||||
// 0x0001 = (uint16_t) STATE_TYPE_NOSPAMKEYS
|
||||
// 0x01ce = (uint16_t) STATE_COOKIE_TYPE
|
||||
// 0x00000000 = (uint32_t) nospam
|
||||
// _ = uint8_t[crypto_box_PUBLICKEYBYTES] public key
|
||||
// _ = uint8_t[crypto_box_SECRETKEYBYTES] secret key
|
||||
const char tox_file[] = "\x00\x00\x00\x00" \
|
||||
"\x1f\x1b\xed\x15" \
|
||||
"\x44\x00\x00\x00" \
|
||||
"\x01\x00" \
|
||||
"\xce\x01" \
|
||||
"\x00\x00\x00\x00";
|
||||
fwrite(tox_file, sizeof(tox_file) - 1, 1, stderr);
|
||||
fwrite(public_key, sizeof(public_key), 1, stderr);
|
||||
fwrite(secret_key, sizeof(secret_key), 1, stderr);
|
||||
|
||||
unsigned char checksum[2] = {0};
|
||||
|
||||
for (size_t i = 0; i < crypto_box_PUBLICKEYBYTES; i ++) {
|
||||
checksum[i % sizeof(checksum)] ^= public_key[i];
|
||||
}
|
||||
|
||||
char checksum_str[sizeof(checksum) * 2 + 1];
|
||||
bin2hex_toupper(checksum_str, sizeof(checksum_str), checksum, sizeof(checksum));
|
||||
char public_key_str[crypto_box_PUBLICKEYBYTES * 2 + 1];
|
||||
bin2hex_toupper(public_key_str, sizeof(public_key_str), public_key, crypto_box_PUBLICKEYBYTES);
|
||||
fprintf(stdout, "Tox Id: %s00000000%s\n", public_key_str, checksum_str);
|
||||
|
||||
return 0;
|
||||
}
|
115
external/toxcore/c-toxcore/other/fun/create_savedata.c
vendored
Normal file
115
external/toxcore/c-toxcore/other/fun/create_savedata.c
vendored
Normal file
@ -0,0 +1,115 @@
|
||||
/* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*
|
||||
* Creates Tox savedata for a given secret key, if provided, or a random key otherwise.
|
||||
* The data is written to stderr, human-readable key info is written to stdout.
|
||||
*
|
||||
* Build: gcc -o create_savedata create_savedata.c -lsodium -ltoxcore -std=c99
|
||||
*
|
||||
* Usage: ./create_savedata [secret-key] 2>data
|
||||
*/
|
||||
#include <stdbool.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <sodium.h>
|
||||
|
||||
#include "../../toxcore/ccompat.h"
|
||||
#include "../../toxcore/tox.h"
|
||||
#include "create_common.h"
|
||||
|
||||
static bool create_tox(const unsigned char *const secret_key, Tox **const tox)
|
||||
{
|
||||
Tox_Err_Options_New options_error;
|
||||
struct Tox_Options *const options = tox_options_new(&options_error);
|
||||
|
||||
if (options_error != TOX_ERR_OPTIONS_NEW_OK) {
|
||||
tox_options_free(options);
|
||||
return false;
|
||||
}
|
||||
|
||||
tox_options_set_savedata_type(options, TOX_SAVEDATA_TYPE_SECRET_KEY);
|
||||
tox_options_set_savedata_data(options, secret_key, crypto_box_SECRETKEYBYTES);
|
||||
Tox_Err_New tox_error;
|
||||
*tox = tox_new(options, &tox_error);
|
||||
|
||||
if (tox_error != TOX_ERR_NEW_OK) {
|
||||
tox_options_free(options);
|
||||
return false;
|
||||
}
|
||||
|
||||
tox_options_free(options);
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool print_savedata(Tox *const tox)
|
||||
{
|
||||
const size_t savedata_size = tox_get_savedata_size(tox);
|
||||
uint8_t *const savedata = (uint8_t *)malloc(savedata_size);
|
||||
|
||||
if (savedata == nullptr) {
|
||||
return false;
|
||||
}
|
||||
|
||||
tox_get_savedata(tox, savedata);
|
||||
fwrite(savedata, savedata_size, 1, stderr);
|
||||
free(savedata);
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool print_tox_id(const Tox *const tox)
|
||||
{
|
||||
uint8_t *const tox_id = (uint8_t *)malloc(tox_address_size());
|
||||
|
||||
if (tox_id == nullptr) {
|
||||
return false;
|
||||
}
|
||||
|
||||
tox_self_get_address(tox, tox_id);
|
||||
const size_t tox_id_str_size = tox_address_size() * 2 + 1;
|
||||
char *const tox_id_str = (char *)malloc(tox_id_str_size);
|
||||
|
||||
if (tox_id_str == nullptr) {
|
||||
free(tox_id);
|
||||
return false;
|
||||
}
|
||||
|
||||
bin2hex_toupper(tox_id_str, tox_id_str_size, tox_id, tox_address_size());
|
||||
fprintf(stdout, "Tox Id: %s\n", tox_id_str);
|
||||
free(tox_id_str);
|
||||
free(tox_id);
|
||||
return true;
|
||||
}
|
||||
|
||||
int main(const int argc, const char *const argv[])
|
||||
{
|
||||
init_sodium();
|
||||
|
||||
unsigned char public_key[crypto_box_PUBLICKEYBYTES];
|
||||
unsigned char secret_key[crypto_box_SECRETKEYBYTES];
|
||||
handle_args(argc, argv, "Creates Tox savedata", public_key, secret_key);
|
||||
|
||||
print_keys(public_key, secret_key);
|
||||
|
||||
Tox *tox;
|
||||
|
||||
if (!create_tox(secret_key, &tox)) {
|
||||
printf("Error: Failed to create a Tox instance.\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!print_savedata(tox)) {
|
||||
printf("Error: Failed to print savedata.\n");
|
||||
tox_kill(tox);
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!print_tox_id(tox)) {
|
||||
printf("Error: Failed to print Tox ID.\n");
|
||||
tox_kill(tox);
|
||||
return 1;
|
||||
}
|
||||
|
||||
tox_kill(tox);
|
||||
|
||||
return 0;
|
||||
}
|
111
external/toxcore/c-toxcore/other/fun/make-funny-savefile.py
vendored
Executable file
111
external/toxcore/c-toxcore/other/fun/make-funny-savefile.py
vendored
Executable file
@ -0,0 +1,111 @@
|
||||
#!/usr/bin/python
|
||||
"""
|
||||
Generate a new (and empty) save file with predefined keys. Used to play
|
||||
with externally generated keys.
|
||||
|
||||
(c) 2015 Alexandre Erwin Ittner
|
||||
|
||||
Distributed under the GNU GPL v3 or later, WITHOUT ANY WARRANTY. See the
|
||||
file "LICENSE.md" for license information.
|
||||
|
||||
|
||||
Usage:
|
||||
|
||||
./make-funny-savefile.py <public key> <private key> <user name> <out file>
|
||||
|
||||
The new user profile will be saved to <out file>.
|
||||
|
||||
The keys must be an hex-encoded valid key pair generated by any means
|
||||
(eg. strkey.c); username may be anything. A random nospam value will be
|
||||
generated.
|
||||
|
||||
Once the savefile is done, load it in your favorite client to get some
|
||||
DHT nodes, set status and status messages, add friends, etc.
|
||||
|
||||
|
||||
Example (of course, do not try using this key for anything real):
|
||||
|
||||
./make-funny-savefile.py 123411DC8B1A4760B648E0C7243B65F01069E4858F45C612CE1A6F673B603830 CC39440CFC063E4A95B7F2FB2580210558BE5C073AFC1C9604D431CCA3132238 "Test user" test.tox
|
||||
|
||||
|
||||
"""
|
||||
import os
|
||||
import struct
|
||||
import sys
|
||||
|
||||
PUBLIC_KEY_LENGTH = 32
|
||||
PRIVATE_KEY_LENGTH = 32
|
||||
|
||||
# Constants taken from messenger.c
|
||||
MESSENGER_STATE_COOKIE_GLOBAL = 0x15ED1B1F
|
||||
MESSENGER_STATE_COOKIE_TYPE = 0x01CE
|
||||
MESSENGER_STATE_TYPE_NOSPAMKEYS = 1
|
||||
MESSENGER_STATE_TYPE_DHT = 2
|
||||
MESSENGER_STATE_TYPE_FRIENDS = 3
|
||||
MESSENGER_STATE_TYPE_NAME = 4
|
||||
MESSENGER_STATE_TYPE_STATUSMESSAGE = 5
|
||||
MESSENGER_STATE_TYPE_STATUS = 6
|
||||
MESSENGER_STATE_TYPE_TCP_RELAY = 10
|
||||
MESSENGER_STATE_TYPE_PATH_NODE = 11
|
||||
|
||||
STATUS_MESSAGE = "New user".encode("utf-8")
|
||||
|
||||
|
||||
def abort(msg: str) -> None:
|
||||
print(msg)
|
||||
exit(1)
|
||||
|
||||
|
||||
if len(sys.argv) != 5:
|
||||
abort("Usage: %s <public key> <private key> <user name> <out file>" %
|
||||
(sys.argv[0]))
|
||||
|
||||
try:
|
||||
public_key = bytes.fromhex(sys.argv[1])
|
||||
except:
|
||||
abort("Bad public key")
|
||||
|
||||
try:
|
||||
private_key = bytes.fromhex(sys.argv[2])
|
||||
except:
|
||||
abort("Bad private key")
|
||||
|
||||
if len(public_key) != PUBLIC_KEY_LENGTH:
|
||||
abort("Public key with wrong length")
|
||||
|
||||
if len(private_key) != PRIVATE_KEY_LENGTH:
|
||||
abort("Private key with wrong length")
|
||||
|
||||
user_name = sys.argv[3].encode("utf-8")
|
||||
|
||||
if len(user_name) > 32:
|
||||
abort("User name too long (for this script, at least)")
|
||||
|
||||
out_file_name = sys.argv[4]
|
||||
nospam = os.urandom(4)
|
||||
|
||||
|
||||
def make_subheader(h_type: int, h_length: int) -> bytes:
|
||||
return (struct.pack("<I", h_length) + struct.pack("<H", h_type) +
|
||||
struct.pack("<H", MESSENGER_STATE_COOKIE_TYPE))
|
||||
|
||||
|
||||
data = (
|
||||
# Main header
|
||||
struct.pack("<I", 0) + struct.pack("<I", MESSENGER_STATE_COOKIE_GLOBAL) +
|
||||
# Keys
|
||||
make_subheader(
|
||||
MESSENGER_STATE_TYPE_NOSPAMKEYS,
|
||||
len(nospam) + PUBLIC_KEY_LENGTH + PRIVATE_KEY_LENGTH,
|
||||
) + nospam + public_key + private_key +
|
||||
# Name (not really needed, but helps)
|
||||
make_subheader(MESSENGER_STATE_TYPE_NAME, len(user_name)) + user_name +
|
||||
# Status message (not really needed, but helps)
|
||||
make_subheader(MESSENGER_STATE_TYPE_STATUSMESSAGE, len(STATUS_MESSAGE)) +
|
||||
STATUS_MESSAGE)
|
||||
|
||||
try:
|
||||
with open(out_file_name, "wb") as fp:
|
||||
fp.write(data)
|
||||
except Exception as e:
|
||||
abort(str(e))
|
172
external/toxcore/c-toxcore/other/fun/save-generator.c
vendored
Normal file
172
external/toxcore/c-toxcore/other/fun/save-generator.c
vendored
Normal file
@ -0,0 +1,172 @@
|
||||
#include <assert.h>
|
||||
#include <stdint.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "../../testing/misc_tools.h"
|
||||
#include "../../toxcore/ccompat.h"
|
||||
#include "../../toxcore/tox.h"
|
||||
|
||||
#define GENERATED_SAVE_FILE "save.tox"
|
||||
#define GENERATED_STATUS_MESSAGE "Hello World"
|
||||
#define GENERATED_REQUEST_MESSAGE "Add me."
|
||||
#define BOOTSTRAP_IP "185.14.30.213"
|
||||
#define BOOTSTRAP_ADDRESS "2555763C8C460495B14157D234DD56B86300A2395554BCAE4621AC345B8C1B1B"
|
||||
#define BOOTSTRAP_UDP_PORT 443
|
||||
|
||||
static bool write_save(const uint8_t *data, size_t length)
|
||||
{
|
||||
FILE *fp = fopen(GENERATED_SAVE_FILE, "wb");
|
||||
|
||||
if (!fp) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (fwrite(data, length, 1, fp) != 1) {
|
||||
fclose(fp);
|
||||
return false;
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool bootstrap_tox(Tox *tox)
|
||||
{
|
||||
uint8_t *key = hex_string_to_bin(BOOTSTRAP_ADDRESS);
|
||||
|
||||
if (!key) {
|
||||
printf("Could not allocate memory for tox address\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
Tox_Err_Bootstrap err;
|
||||
tox_bootstrap(tox, BOOTSTRAP_IP, BOOTSTRAP_UDP_PORT, key, &err);
|
||||
free(key);
|
||||
|
||||
if (err != TOX_ERR_BOOTSTRAP_OK) {
|
||||
printf("Failed to bootstrap. Error number: %d", err);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static void tox_connection_callback(Tox *tox, Tox_Connection connection, void *userdata)
|
||||
{
|
||||
if (connection == TOX_CONNECTION_UDP) {
|
||||
printf("Connected to the tox network.\n");
|
||||
*(bool *)userdata = true;
|
||||
}
|
||||
}
|
||||
|
||||
static void print_information(Tox *tox)
|
||||
{
|
||||
uint8_t tox_id[TOX_ADDRESS_SIZE];
|
||||
char tox_id_str[TOX_ADDRESS_SIZE * 2];
|
||||
tox_self_get_address(tox, tox_id);
|
||||
to_hex(tox_id_str, tox_id, TOX_ADDRESS_SIZE);
|
||||
|
||||
char nospam_str[(TOX_NOSPAM_SIZE * 2) + 1];
|
||||
uint32_t nospam = tox_self_get_nospam(tox);
|
||||
int length = snprintf(nospam_str, sizeof(nospam_str), "%08X", nospam);
|
||||
nospam_str[length] = '\0';
|
||||
|
||||
uint8_t *name = (uint8_t *)malloc(tox_self_get_name_size(tox) + 1);
|
||||
assert(name != nullptr);
|
||||
tox_self_get_name(tox, name);
|
||||
name[tox_self_get_name_size(tox)] = '\0';
|
||||
|
||||
printf("INFORMATION\n");
|
||||
printf("----------------------------------\n");
|
||||
printf("Tox ID: %.*s.\n", (int)TOX_ADDRESS_SIZE * 2, tox_id_str);
|
||||
printf("Nospam: %s.\n", nospam_str);
|
||||
printf("Name: %s.\n", name);
|
||||
printf("Status message: %s.\n", GENERATED_STATUS_MESSAGE);
|
||||
printf("Number of friends: %zu.\n", tox_self_get_friend_list_size(tox));
|
||||
printf("----------------------------------\n");
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
if (argc < 3) {
|
||||
printf("Usage: ./save-generator <name> <friend id> ...\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
Tox *tox = tox_new(nullptr, nullptr);
|
||||
|
||||
if (!tox) {
|
||||
printf("Failed to create tox.\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!bootstrap_tox(tox)) {
|
||||
tox_kill(tox);
|
||||
return -1;
|
||||
}
|
||||
|
||||
tox_callback_self_connection_status(tox, tox_connection_callback);
|
||||
|
||||
bool connected = false;
|
||||
|
||||
while (!connected) {
|
||||
tox_iterate(tox, &connected);
|
||||
c_sleep(tox_iteration_interval(tox));
|
||||
}
|
||||
|
||||
Tox_Err_Set_Info err;
|
||||
const uint8_t *name = (uint8_t *)argv[1];
|
||||
tox_self_set_name(tox, name, strlen((const char *)name), &err);
|
||||
|
||||
if (err != TOX_ERR_SET_INFO_OK) {
|
||||
printf("Failed to set name. Error number %d\n", err);
|
||||
}
|
||||
|
||||
tox_self_set_status_message(tox, (const uint8_t *)GENERATED_STATUS_MESSAGE, strlen(GENERATED_STATUS_MESSAGE), &err);
|
||||
|
||||
if (err != TOX_ERR_SET_INFO_OK) {
|
||||
printf("Failed to set status. Error number: %d\n", err);
|
||||
}
|
||||
|
||||
for (unsigned int i = 2; i < argc; i++) { //start at 2 because that is where the tox ids are
|
||||
uint8_t *address = hex_string_to_bin(argv[i]);
|
||||
Tox_Err_Friend_Add friend_err;
|
||||
tox_friend_add(tox, address, (const uint8_t *)GENERATED_REQUEST_MESSAGE, strlen(GENERATED_REQUEST_MESSAGE),
|
||||
&friend_err);
|
||||
free(address);
|
||||
|
||||
if (friend_err != TOX_ERR_FRIEND_ADD_OK) {
|
||||
printf("Failed to add friend number %u. Error number: %d\n", i - 1, friend_err);
|
||||
}
|
||||
}
|
||||
|
||||
const size_t length = tox_get_savedata_size(tox);
|
||||
uint8_t *savedata = (uint8_t *)malloc(length);
|
||||
|
||||
if (!savedata) {
|
||||
printf("Could not allocate memory for savedata.\n");
|
||||
tox_kill(tox);
|
||||
return -1;
|
||||
}
|
||||
|
||||
tox_get_savedata(tox, savedata);
|
||||
|
||||
bool ret = write_save(savedata, length);
|
||||
free(savedata);
|
||||
|
||||
if (!ret) {
|
||||
printf("Failed to write save.\n");
|
||||
tox_kill(tox);
|
||||
return -1;
|
||||
}
|
||||
|
||||
printf("Wrote tox save to %s\n", GENERATED_SAVE_FILE);
|
||||
|
||||
print_information(tox);
|
||||
|
||||
tox_kill(tox);
|
||||
|
||||
return 0;
|
||||
}
|
147
external/toxcore/c-toxcore/other/fun/sign.c
vendored
Normal file
147
external/toxcore/c-toxcore/other/fun/sign.c
vendored
Normal file
@ -0,0 +1,147 @@
|
||||
/* Binary signer/checker using ed25519
|
||||
*
|
||||
* Compile with:
|
||||
* gcc -o sign sign.c -lsodium
|
||||
*
|
||||
* Generate a keypair:
|
||||
* ./sign g
|
||||
*
|
||||
* Sign a file:
|
||||
* ./sign s PRIVATEKEY file.bin signedfile.bin
|
||||
*
|
||||
* Check a file:
|
||||
*
|
||||
* ./sign c PUBKEY signedfile.bin
|
||||
*
|
||||
* NOTE: The signature is appended to the end of the file.
|
||||
*/
|
||||
#include <sodium.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "../../testing/misc_tools.h" // hex_string_to_bin
|
||||
#include "../../toxcore/ccompat.h"
|
||||
|
||||
static int load_file(char *filename, unsigned char **result)
|
||||
{
|
||||
int size = 0;
|
||||
FILE *f = fopen(filename, "rb");
|
||||
|
||||
if (f == nullptr) {
|
||||
*result = nullptr;
|
||||
return -1; // -1 means file opening fail
|
||||
}
|
||||
|
||||
fseek(f, 0, SEEK_END);
|
||||
size = ftell(f);
|
||||
fseek(f, 0, SEEK_SET);
|
||||
*result = (unsigned char *)malloc(size + 1);
|
||||
|
||||
if (size != fread(*result, sizeof(char), size, f)) {
|
||||
free(*result);
|
||||
fclose(f);
|
||||
return -2; // -2 means file reading fail
|
||||
}
|
||||
|
||||
fclose(f);
|
||||
(*result)[size] = 0;
|
||||
return size;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
unsigned char pk[crypto_sign_ed25519_PUBLICKEYBYTES];
|
||||
unsigned char sk[crypto_sign_ed25519_SECRETKEYBYTES];
|
||||
|
||||
if (argc == 2 && argv[1][0] == 'g') {
|
||||
crypto_sign_ed25519_keypair(pk, sk);
|
||||
printf("Public key:\n");
|
||||
|
||||
for (int i = 0; i < crypto_sign_ed25519_PUBLICKEYBYTES; ++i) {
|
||||
printf("%02X", pk[i]);
|
||||
}
|
||||
|
||||
printf("\nSecret key:\n");
|
||||
|
||||
for (int i = 0; i < crypto_sign_ed25519_SECRETKEYBYTES; ++i) {
|
||||
printf("%02X", sk[i]);
|
||||
}
|
||||
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
if (argc == 5 && argv[1][0] == 's') {
|
||||
unsigned char *secret_key = hex_string_to_bin(argv[2]);
|
||||
unsigned char *data = nullptr;
|
||||
int size = load_file(argv[3], &data);
|
||||
|
||||
if (size < 0) {
|
||||
goto fail;
|
||||
}
|
||||
|
||||
unsigned long long smlen;
|
||||
unsigned char *sm = (unsigned char *)malloc(size + crypto_sign_ed25519_BYTES * 2);
|
||||
crypto_sign_ed25519(sm, &smlen, data, size, secret_key);
|
||||
free(data);
|
||||
free(secret_key);
|
||||
|
||||
if (smlen - size != crypto_sign_ed25519_BYTES) {
|
||||
free(sm);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
FILE *f = fopen(argv[4], "wb");
|
||||
|
||||
if (f == nullptr) {
|
||||
free(sm);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
memcpy(sm + smlen, sm, crypto_sign_ed25519_BYTES); // Move signature from beginning to end of file.
|
||||
|
||||
if (fwrite(sm + (smlen - size), 1, smlen, f) != smlen) {
|
||||
fclose(f);
|
||||
free(sm);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
fclose(f);
|
||||
free(sm);
|
||||
printf("Signed successfully.\n");
|
||||
}
|
||||
|
||||
if (argc == 4 && argv[1][0] == 'c') {
|
||||
unsigned char *public_key = hex_string_to_bin(argv[2]);
|
||||
unsigned char *data;
|
||||
int size = load_file(argv[3], &data);
|
||||
|
||||
if (size < 0) {
|
||||
goto fail;
|
||||
}
|
||||
|
||||
unsigned char *signe = (unsigned char *)malloc(size + crypto_sign_ed25519_BYTES);
|
||||
memcpy(signe, data + size - crypto_sign_ed25519_BYTES,
|
||||
crypto_sign_ed25519_BYTES); // Move signature from end to beginning of file.
|
||||
memcpy(signe + crypto_sign_ed25519_BYTES, data, size - crypto_sign_ed25519_BYTES);
|
||||
free(data);
|
||||
|
||||
unsigned char *m = (unsigned char *)malloc(size);
|
||||
unsigned long long mlen;
|
||||
|
||||
if (crypto_sign_ed25519_open(m, &mlen, signe, size, public_key) == -1) {
|
||||
printf("Failed checking sig.\n");
|
||||
free(m);
|
||||
free(signe);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
free(m);
|
||||
free(signe);
|
||||
printf("Checked successfully.\n");
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
printf("FAIL\n");
|
||||
return 1;
|
||||
}
|
151
external/toxcore/c-toxcore/other/fun/strkey.c
vendored
Normal file
151
external/toxcore/c-toxcore/other/fun/strkey.c
vendored
Normal file
@ -0,0 +1,151 @@
|
||||
/* strkey -- String in Public Key
|
||||
*
|
||||
* Generates Tox's key pairs, checking if a certain string is in the public key.
|
||||
*
|
||||
* Requires sodium or nacl library.
|
||||
*
|
||||
* There seem to be some problems with the code working on Windows -- it works
|
||||
* when built in debug mode with MinGW 4.8, but it doesn't work correctly when
|
||||
* built in release.
|
||||
*
|
||||
* Usage: strkey <offset> <string>
|
||||
*
|
||||
* Offset - an integer specifying exact byte offset position of the string you
|
||||
* are looking for within a public key. When offset is negative, the program
|
||||
* just looks for the desired string being somewhere, doesn't matter where, in
|
||||
* the public key.
|
||||
*
|
||||
* String - a hex string that you want to have in your public key. It must have
|
||||
* an even number of letters, since every two hexes map to a single byte of
|
||||
* the public key.
|
||||
*
|
||||
* Examples:
|
||||
* strkey 0 0123
|
||||
* Looks for a public key that begins with "0123".
|
||||
*
|
||||
* strkey 1 0123
|
||||
* Looks for a public key that has "0123" starting at its second byte, i.e. "XX0123...".
|
||||
*
|
||||
* strkey 2 0123
|
||||
* Looks for a public key that has "0123" starting at its third byte, i.e. "XXXX0123...".
|
||||
* (each two hexes represent a single byte of a public key)
|
||||
*
|
||||
* strkey -1 AF57CC
|
||||
* Looks for a public key that contains "AF57CC", regardless of its position.
|
||||
*
|
||||
* To compile with gcc and sodium: gcc strkey.c -o strkey -lsodium
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <sodium.h>
|
||||
|
||||
#include "../../toxcore/ccompat.h"
|
||||
|
||||
#define PRINT_TRIES_COUNT
|
||||
|
||||
static void print_key(unsigned char *key)
|
||||
{
|
||||
for (size_t i = 0; i < crypto_box_PUBLICKEYBYTES; ++i) {
|
||||
if (key[i] < 16) {
|
||||
fprintf(stdout, "0");
|
||||
}
|
||||
|
||||
fprintf(stdout, "%hhX", key[i]);
|
||||
}
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
unsigned char public_key[crypto_box_PUBLICKEYBYTES]; // null terminator
|
||||
unsigned char secret_key[crypto_box_SECRETKEYBYTES];
|
||||
long int offset = 0;
|
||||
size_t len;
|
||||
unsigned char desired_bin[crypto_box_PUBLICKEYBYTES]; // null terminator
|
||||
|
||||
if (argc == 3) {
|
||||
offset = strtol(argv[1], nullptr, 10);
|
||||
|
||||
if (offset <= 0) {
|
||||
fprintf(stderr, "strtol() failed to convert \"%s\" into an integer\n", argv[1]);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
char *desired_hex = argv[2];
|
||||
len = strlen(desired_hex);
|
||||
|
||||
if (len % 2 != 0) {
|
||||
fprintf(stderr, "Desired key should have an even number of letters\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
size_t block_length = (offset < 0 ? 0 : offset) + len / 2;
|
||||
|
||||
if (block_length > crypto_box_PUBLICKEYBYTES) {
|
||||
fprintf(stderr, "The given key with the given offset exceed public key's length\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
// convert hex to bin
|
||||
char *pos = desired_hex;
|
||||
size_t i;
|
||||
|
||||
for (i = 0; i < len; pos += 2) {
|
||||
unsigned int value;
|
||||
sscanf(pos, "%02x", &value);
|
||||
desired_bin[i] = value;
|
||||
++i;
|
||||
}
|
||||
} else {
|
||||
fprintf(stdout, "Usage: executable <byte offset> <desired hex string with even number of letters>\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
len /= 2;
|
||||
|
||||
#ifdef PRINT_TRIES_COUNT
|
||||
long long unsigned int tries = 0;
|
||||
#endif
|
||||
|
||||
if (offset < 0) {
|
||||
int found = 0;
|
||||
|
||||
do {
|
||||
#ifdef PRINT_TRIES_COUNT
|
||||
++tries;
|
||||
#endif
|
||||
crypto_box_keypair(public_key, secret_key);
|
||||
|
||||
for (int i = 0; i <= crypto_box_PUBLICKEYBYTES - len; ++i) {
|
||||
if (memcmp(public_key + i, desired_bin, len) == 0) {
|
||||
found = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
} while (!found);
|
||||
} else {
|
||||
unsigned char *p = public_key + offset;
|
||||
|
||||
do {
|
||||
#ifdef PRINT_TRIES_COUNT
|
||||
++tries;
|
||||
#endif
|
||||
crypto_box_keypair(public_key, secret_key);
|
||||
} while (memcmp(p, desired_bin, len) != 0);
|
||||
}
|
||||
|
||||
fprintf(stdout, "Public key: ");
|
||||
print_key(public_key);
|
||||
fprintf(stdout, "\n");
|
||||
|
||||
fprintf(stdout, "Private key: ");
|
||||
print_key(secret_key);
|
||||
fprintf(stdout, "\n");
|
||||
|
||||
#ifdef PRINT_TRIES_COUNT
|
||||
fprintf(stdout, "Found the key pair on %llu try.\n", tries);
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
Reference in New Issue
Block a user