#include #include #include "pico/stdlib.h" #include "pico/stdio_usb.h" #include "pico/cyw43_arch.h" #include "hardware/pio.h" #include "board.h" #include "config.h" #include "channels.h" #include "dmx_out.h" #include "artnet.h" #include "wifi_mgr.h" #include "http_server.h" static dmx_out_t g_dmx[BOARD_NUM_UNIVERSES]; static uint8_t g_frames[BOARD_NUM_UNIVERSES][BOARD_DMX_FRAME_LEN]; static bool dmx_timer_cb(repeating_timer_t *rt) { (void)rt; for (unsigned u = 0; u < BOARD_NUM_UNIVERSES; u++) { if (dmx_out_busy(&g_dmx[u])) { continue; } channels_build_frame(u, g_frames[u]); dmx_out_write(&g_dmx[u], g_frames[u], BOARD_DMX_FRAME_LEN); } return true; } int main(void) { stdio_init_all(); /* Give USB CDC a moment so early boot logs are visible after flash/reboot. */ for (int i = 0; i < 40 && !stdio_usb_connected(); i++) { sleep_ms(50); } sleep_ms(200); printf("\nArtNetDMX starting\n"); fflush(stdout); config_init(); channels_init(); if (!dmx_out_init(&g_dmx[0], BOARD_DMX_A_PIN, pio0)) { printf("DMX A init failed\n"); } if (!dmx_out_init(&g_dmx[1], BOARD_DMX_B_PIN, pio1)) { printf("DMX B init failed\n"); } if (!wifi_mgr_start(config_get())) { printf("WiFi start failed\n"); while (true) { tight_loop_contents(); } } if (!http_server_start()) { printf("HTTP start failed\n"); } if (!artnet_start()) { printf("Art-Net start failed\n"); } static repeating_timer_t dmx_timer; if (!add_repeating_timer_ms(-BOARD_DMX_PERIOD_MS, dmx_timer_cb, NULL, &dmx_timer)) { printf("DMX timer failed\n"); } else { printf("DMX output at %d Hz\n", BOARD_DMX_HZ); } printf("Ready — mode=%s primary=%s mDNS http://%s/\n", wifi_mode_name(wifi_mgr_active_mode()), wifi_mgr_ip_str(), wifi_mgr_mdns_name()); if (wifi_mgr_ap_up()) { printf("SoftAP http://%s/ (ssid ArtNetDMX)\n", wifi_mgr_ap_ip_str()); } else { printf("Joining STA (SoftAP starts only if join fails)...\n"); } while (true) { wifi_mgr_poll(); artnet_poll(); tight_loop_contents(); sleep_ms(10); } }