#define _POSIX_C_SOURCE 200809L #define main cable_thang_embedded_main #include "../src/ddat_gui.c" #undef main #include #include #include static void announce_new_messages(gui_state_t *state, size_t *seen) { uint8_t self[32]; size_t i; if (cable_hex_key(state->cable_feed_key, self)) return; for (i = *seen; i < state->cable_line_count; i++) { const cable_room_event_t *event = &state->cable_lines[i].event; if (event->type == CABLE_ROOM_TEXT && memcmp(event->sender, self, sizeof(self)) != 0) { printf("RX\t%s\t%s\n", event->nick, event->text); fflush(stdout); } } *seen = state->cable_line_count; } static void read_command(gui_state_t *state, char *line, int *running) { size_t length = strlen(line); while (length && (line[length - 1] == '\n' || line[length - 1] == '\r')) line[--length] = '\0'; if (!strcmp(line, "QUIT")) { *running = 0; return; } if (!strncmp(line, "SEND ", 5)) { if (strlen(line + 5) > CABLE_CHAT_TEXT_BYTES) { puts("ERR message-too-long"); fflush(stdout); return; } strcpy(state->cable_input, line + 5); if (cable_room_submit(state)) { puts("ERR send-failed"); fflush(stdout); } else { puts("SENT"); fflush(stdout); } return; } if (!strncmp(line, "NICK ", 5)) { if (strlen(line + 5) > CABLE_ROOM_NICK_BYTES) { puts("ERR nick-too-long"); fflush(stdout); return; } snprintf(state->cable_input, sizeof(state->cable_input), "/nick %s", line + 5); if (cable_room_submit(state)) { puts("ERR nick-failed"); fflush(stdout); } else { puts("NICKED"); fflush(stdout); } return; } if (!strncmp(line, "JOIN ", 5)) { if (strlen(line + 5) > CABLE_ROOM_CHANNEL_BYTES) { puts("ERR channel-too-long"); fflush(stdout); return; } snprintf(state->cable_input, sizeof(state->cable_input), "/join %s", line + 5); if (cable_room_submit(state)) { puts("ERR join-failed"); fflush(stdout); } else { puts("JOINED"); fflush(stdout); } return; } puts("ERR unknown-command"); fflush(stdout); } int main(int argc, char **argv) { static gui_state_t state; SDL_Window *window; SDL_Renderer *renderer; char input[2048]; size_t seen_lines = 0; int running = 1, ready_reported = 0, peer_reported = 0; if (argc != 2) { fputs("usage: test_cable_thang \n", stderr); return 2; } if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER) != 0) { fprintf(stderr, "SDL init: %s\n", SDL_GetError()); return 1; } window = SDL_CreateWindow("cable-thang live test", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, 1000, 640, SDL_WINDOW_HIDDEN | SDL_WINDOW_RESIZABLE); if (!window) { fprintf(stderr, "SDL window: %s\n", SDL_GetError()); SDL_Quit(); return 1; } renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_SOFTWARE); if (!renderer) { fprintf(stderr, "SDL renderer: %s\n", SDL_GetError()); SDL_DestroyWindow(window); SDL_Quit(); return 1; } state.cable_thang_mode = 1; if (cable_thang_room_init(&state, argv[1]) || cable_thang_network_start(&state)) { perror("Cable SDL room startup"); SDL_DestroyRenderer(renderer); SDL_DestroyWindow(window); SDL_Quit(); return 1; } while (running) { fd_set reads; struct timeval tick = {0, 10000}; int result; SDL_Event event; while (SDL_PollEvent(&event)) if (event.type == SDL_QUIT) running = 0; network_pump(&state, SDL_GetTicks()); if (!ready_reported && state.cable_feed_key[0]) { printf("C_READY %s\n", state.cable_feed_key); fflush(stdout); ready_reported = 1; } if (!peer_reported && state.connected_peers) { puts("PEER_UP"); fflush(stdout); peer_reported = 1; } announce_new_messages(&state, &seen_lines); cable_thang_draw(renderer, 1000, 640, &state); SDL_RenderPresent(renderer); FD_ZERO(&reads); FD_SET(STDIN_FILENO, &reads); result = select(STDIN_FILENO + 1, &reads, NULL, NULL, &tick); if (result > 0 && FD_ISSET(STDIN_FILENO, &reads)) { if (!fgets(input, sizeof(input), stdin)) running = 0; else read_command(&state, input, &running); } else if (result < 0 && errno != EINTR) running = 0; } network_stop(&state); SDL_DestroyRenderer(renderer); SDL_DestroyWindow(window); SDL_Quit(); return 0; }