Merge pull request #148 from feelfree69/syslog

Syslog: Duplicates console output to remote syslog server; Web-Interface: Send console commands to device
This commit is contained in:
logicog
2026-04-27 20:30:39 +02:00
committed by GitHub
20 changed files with 291 additions and 28 deletions
+2 -2
View File
@@ -28,8 +28,8 @@ create_build_dir:
mkdir -p $(BUILDDIR)/httpd
SRCS = rtlplayground.c rtl837x_flash.c rtl837x_leds.c rtl837x_phy.c rtl837x_port.c cmd_parser.c html_data.c rtl837x_igmp.c
SRCS += rtl837x_stp.c rtl837x_pins.c dhcp.c machine.c cmd_editor.c rtl837x_bandwidth.c rtl837x_init.c
SRCS += uip/timer.c uip/uip.c uip/uip_arp.c uip/uiplib.c uip/uip-fw.c uip/uip-neighbor.c uip/uip-split.c
SRCS += rtl837x_stp.c rtl837x_pins.c dhcp.c machine.c cmd_editor.c rtl837x_bandwidth.c rtl837x_init.c syslog.c
SRCS += uip/timer.c uip/uip.c uip/uip_arp.c uip/uiplib.c uip/uip-fw.c uip/uip-neighbor.c uip/uip-split.c udp_apps.c
SRCS += httpd/httpd.c httpd/page_impl.c
OBJS = ${SRCS:%.c=$(BUILDDIR)/%.rel}
DEPS := ${SRCS:%.c=$(BUILDDIR)/%.d}
+1 -1
View File
@@ -197,7 +197,7 @@ void cmd_edit(void) __banked
if (cmd_line_len)
cmd_available = 1;
else
print_string("\n> ");
print_cmd_prompt();
cursor = 0;
cmd_line_len = 0;
history_editptr = 0xffff;
+49
View File
@@ -15,6 +15,7 @@
#include "rtl837x_igmp.h"
#include "rtl837x_bandwidth.h"
#include "dhcp.h"
#include "syslog.h"
#include "uip/uip.h"
#include "version.h"
@@ -1188,6 +1189,52 @@ err:
print_string("usage: bw [in|out|status] <port> [<hexvalue>|off|drop|fc]\n");
}
void parse_syslog(void)
{
if (cmd_words_len < 2) // no argument -> print status
{
print_string("Current syslog status: ");
if (syslog_state.enabled) {
print_string("enabled, sending to ");
itoa(syslog_state.server_ip[0]); write_char('.'); itoa(syslog_state.server_ip[1]); write_char('.');
itoa(syslog_state.server_ip[2]); write_char('.'); itoa(syslog_state.server_ip[3]);
write_char('\n');
} else {
print_string("disabled\n");
}
return;
}
if (cmd_compare(1, "on")) {
syslog_start();
} else if (cmd_compare(1, "off")){
syslog_stop();
} else if (cmd_compare(1, "ip")) {
if (cmd_words_len < 3) { // no additional arguemnt -> print current ip
print_string("Current syslog IP: ");
itoa(syslog_state.server_ip[0]); write_char('.'); itoa(syslog_state.server_ip[1]); write_char('.');
itoa(syslog_state.server_ip[2]); write_char('.'); itoa(syslog_state.server_ip[3]);
return;
} else if (!parse_ip(cmd_words_b[2])) {
uint8_t was_enabled = syslog_state.enabled;
if (was_enabled)
syslog_stop();
print_string("Setting new syslog IP.\n");
syslog_state.server_ip[0] = ip[0]; syslog_state.server_ip[1] = ip[1];
syslog_state.server_ip[2] = ip[2]; syslog_state.server_ip[3] = ip[3];
if (was_enabled)
syslog_start();
} else {
print_string("Invalid IP address\n");
}
}
else
{
print_string("Error: syslog [on|off|ip [ip-address]]\n");
print_string(" on/off enables or disables syslog, ip sets the syslog server IP address\n");
}
}
// Parse command into words
// cmd_words_len contains the number of words found.
// cmd_words_b[] contains only start of a word offset.
@@ -1339,6 +1386,8 @@ void cmd_parser(void) __banked
parse_port();
} else if (cmd_compare(0, "mtu")) {
parse_mtu();
} else if (cmd_compare(0, "syslog")) {
parse_syslog();
} else if (cmd_compare(0, "ip")) {
if (cmd_compare(1, "dhcp")) {
dhcp_start();
+3 -1
View File
@@ -348,8 +348,10 @@ void dhcp_stop(void) __banked
}
void dhcp_callback(void) __banked
void dhcp_callback(uint16_t lport) __banked
{
if (lport != HTONS(DHCPC_CLIENT_PORT)) // Is this call for us? If not, ignore it
return;
if (!dhcp_state.state)
return;
if (uip_closed()) {
+1 -6
View File
@@ -16,7 +16,7 @@
void dhcp_start(void) __banked;
void dhcp_stop(void) __banked;
// void dhcp_periodic(void) __banked;
void dhcp_callback(void) __banked;
void dhcp_callback(uint16_t lport) __banked;
struct dhcp_state {
@@ -40,9 +40,4 @@ struct dhcp_state {
typedef struct dhcp_state uip_udp_appstate_t;
/* Finally we define the application function to be called by uIP. */
#ifndef UIP_UDP_APPCALL
#define UIP_UDP_APPCALL dhcp_callback
#endif /* UIP_APPCALL */
#endif
+12
View File
@@ -16,6 +16,7 @@
<div class="tab-bar">
<button class="tab-btn active" onclick="openTab(event, 'system-tab')">System</button>
<button class="tab-btn" onclick="openTab(event, 'advanced-tab')">Advanced</button>
<button class="tab-btn" onclick="openTab(event, 'console-tab')">Console</button>
</div>
<nav id="sidebar"></nav>
<div style="margin-left:16%;padding:1px 16px;height:1000px;">
@@ -56,6 +57,17 @@
<input style="width:40%;" class="action" id="switch_reset" onclick="resetSwitch();" type="button" value="Reset Switch">
</div>
<div id="console-tab" class="tab-content">
<h1>Console Command</h1>
<label for="console_command">Enter command:</label>
<input type="text" id="console_cmd" name="console_cmd" style="width:40%;">
<input style="width:20%;" class="action" id="cmd_sub" onclick="cmdSub();" type="button" value="Send Command"><br/>
<br/><br/>
Be careful when entering console commands, you can lock yourself out!<br/>
</div>
</div>
<script src="/config.js"></script>
<script src="/system.js"></script>
+14
View File
@@ -27,6 +27,20 @@ async function ipSub() {
}
}
async function cmdSub() {
var cmd = document.getElementById('console_cmd').value;
try {
const response = await fetch('/cmd', {
method: 'POST',
body: cmd
});
console.log('Completed!', response);
} catch(err) {
console.error(`Error: ${err}`);
}
}
async function sendConfig(c) {
const form = new FormData();
form.append("MAX_FILE_SIZE", "4096");
+6 -1
View File
@@ -13,11 +13,11 @@
#include "version.h"
#include "machine.h"
#include "page_impl.h"
#include "syslog.h"
// #define DEBUG
#include "debug.h"
#define L2_MAX_TRANSFER 30
#pragma codeseg BANK1
@@ -227,6 +227,11 @@ void send_basic_info(void)
itoa_html(uip_netmask[0] >> 8); char_to_html('.');
itoa_html(uip_netmask[1]); char_to_html('.');
itoa_html(uip_netmask[1] >> 8);
slen += strtox(outbuf + slen, "\",\"syslog_server_ip\":\"");
itoa_html(syslog_state.server_ip[0]); char_to_html('.');
itoa_html(syslog_state.server_ip[1]); char_to_html('.');
itoa_html(syslog_state.server_ip[2]); char_to_html('.');
itoa_html(syslog_state.server_ip[3]);
slen += strtox(outbuf + slen, "\",\"mac_address\":\"");
byte_to_html(uip_ethaddr.addr[0]); char_to_html(':');
byte_to_html(uip_ethaddr.addr[1]); char_to_html(':');
+3
View File
@@ -110,6 +110,7 @@ extern __xdata uint8_t uip_buf[UIP_CONF_BUFFER_SIZE+2];
extern __xdata struct uip_eth_addr uip_ethaddr;
// Headers for calls in the common code area (HOME/BANK0)
void print_string_no_syslog(__code char *p);
void print_string(__code char *p);
void print_string_x(__xdata char *p);
void print_long(uint32_t a);
@@ -118,6 +119,7 @@ void print_byte(uint8_t a);
void itoa(uint8_t v);
void print_sfr_data(void);
void print_phy_data(void);
void print_cmd_prompt(void);
void phy_write_mask(uint16_t phy_mask, uint8_t dev_id, uint16_t reg, uint16_t v);
void phy_write(uint8_t phy_id, uint8_t dev_id, uint16_t reg, uint16_t v);
void phy_read(uint8_t phy_id, uint8_t dev_id, uint16_t reg);
@@ -130,6 +132,7 @@ void sds_read(uint8_t sds_id, uint8_t page, uint8_t reg);
void sds_write_v(uint8_t sds_id, uint8_t page, uint8_t reg, uint16_t v);
void delay(uint16_t t);
void sleep(uint16_t t);
void write_char_no_syslog(char c);
void write_char(char c);
void print_reg(uint16_t reg);
uint8_t sfp_read_reg(uint8_t slot, uint8_t reg);
+1
View File
@@ -13,3 +13,4 @@ void flash_write_bytes(__xdata uint8_t *ptr);
__code char* get_flash_size_str(void);
#endif
+10 -7
View File
@@ -2,7 +2,10 @@
#include "rtl837x_common.h"
#include "rtl837x_regs.h"
uint8_t i2c_bus_from_sda_pin(uint8_t sda_pin) {
#pragma codeseg BANK2
#pragma constseg BANK2
uint8_t i2c_bus_from_sda_pin(uint8_t sda_pin) __banked {
switch (sda_pin) {
case GPIO47_I2C_SDA0:
return 0;
@@ -19,7 +22,7 @@ uint8_t i2c_bus_from_sda_pin(uint8_t sda_pin) {
}
}
uint8_t i2c_bus_from_scl_pin(uint8_t scl_pin) {
uint8_t i2c_bus_from_scl_pin(uint8_t scl_pin) __banked{
switch (scl_pin) {
case GPIO46_I2C_SCL0:
return 0;
@@ -35,18 +38,18 @@ uint8_t i2c_bus_from_scl_pin(uint8_t scl_pin) {
}
/* Returns RTL837X_REG_GPIO_XX_OUTPUT register address */
static uint16_t gpio_output_reg(uint8_t pin) {
static uint16_t gpio_output_reg(uint8_t pin) __banked{
return pin < 32 ? RTL837X_REG_GPIO_00_31_OUTPUT : RTL837X_REG_GPIO_32_63_OUTPUT;
}
/* Returns RTL837X_REG_GPIO_XX_DIRECTION register address */
static uint16_t gpio_direction_reg(uint8_t pin) {
static uint16_t gpio_direction_reg(uint8_t pin) __banked {
return pin < 32 ? RTL837X_REG_GPIO_00_31_DIRECTION : RTL837X_REG_GPIO_32_63_DIRECTION;
}
/* Enable GPIO functions for pin */
static void gpio_mux_setup(uint8_t pin)
static void gpio_mux_setup(uint8_t pin) __banked
{
// Some GPIOs require setting MUX registers to enable GPIO
switch (pin) {
@@ -94,7 +97,7 @@ static void gpio_mux_setup(uint8_t pin)
}
}
void gpio_input_setup(uint8_t pin) {
void gpio_input_setup(uint8_t pin) __banked {
if (pin == GPIO_NA) {
return;
}
@@ -103,7 +106,7 @@ void gpio_input_setup(uint8_t pin) {
reg_bit_clear(gpio_direction_reg(pin), (pin % 32));
}
void gpio_output_setup(uint8_t pin, __xdata uint8_t initial_val) {
void gpio_output_setup(uint8_t pin, __xdata uint8_t initial_val) __banked{
if (pin == GPIO_NA) {
return;
}
+4 -4
View File
@@ -72,22 +72,22 @@
#define GPIO_NA 0xFF
/* Convert SDA PIN GPIO to I2C bus number */
uint8_t i2c_bus_from_sda_pin(uint8_t sda_pin);
uint8_t i2c_bus_from_sda_pin(uint8_t sda_pin) __banked;
/* Convert SCL PIN GPIO to I2C bus number */
uint8_t i2c_bus_from_scl_pin(uint8_t scl_pin);
uint8_t i2c_bus_from_scl_pin(uint8_t scl_pin) __banked;
/*
* Setup a GPIO pin as input
* pin: GPIO pin number 0-63
*/
void gpio_input_setup(uint8_t pin);
void gpio_input_setup(uint8_t pin) __banked;
/*
* Setup a GPIO pin as output
* pin: GPIO pin number 0-63
* initial_val: 1 for bit set in RTL837X_REG_GPIO_xx_OUTPUT, 0 for bit not set
*/
void gpio_output_setup(uint8_t pin, __xdata uint8_t initial_val);
void gpio_output_setup(uint8_t pin, __xdata uint8_t initial_val) __banked;
#endif
+1 -1
View File
@@ -387,7 +387,7 @@ void port_l2_setup(void) __banked
void port_stats_print(void) __banked
{
print_string("\n Port\tState\tLink\tTxGood\t\tTxBad\t\tRxGood\t\tRxBad\n");
print_string("\nPort\tState\tLink\tTxGood\t\tTxBad\t\tRxGood\t\tRxBad\n");
for (uint8_t i = machine.min_port; i <= machine.max_port; i++) {
write_char('0' + machine.log_to_phys_port[i]); write_char('\t');
+29 -3
View File
@@ -24,6 +24,7 @@
#include "uip/uip_arp.h"
#include "machine.h"
#include "phy.h"
#include "syslog.h"
extern __code const struct machine machine;
extern __xdata uint32_t flash_size;
@@ -216,7 +217,7 @@ void isr_serial(void) __interrupt(4)
}
void write_char(char c)
void write_char_no_syslog(char c)
{
do {
} while (tx_buf_empty == 0);
@@ -230,6 +231,17 @@ void write_char(char c)
SBUF = c;
}
void write_char(char c)
{
write_char_no_syslog(c);
if (syslog_state.enabled) {
logbuf[syslog_state.writeptr++] = c;
syslog_state.writeptr &= (LOGBUF_SIZE - 1);
if (c == '\n')
syslog_state.line_available = 1;
}
}
void itoa(uint8_t v)
{
@@ -253,6 +265,12 @@ void print_string(__code char *p)
write_char(*p++);
}
void print_string_no_syslog(__code char *p)
{
while (*p)
write_char_no_syslog(*p++);
}
void print_string_x(__xdata char *p)
{
while (*p)
@@ -350,6 +368,11 @@ void print_byte(uint8_t a)
write_char(low);
}
void print_cmd_prompt(void)
{
print_string_no_syslog("\n> ");
}
/*
* External IRQ 0 Service Routine: Called on link change?
* Note that all registers are being put on the STACK because of calling a subroutine
@@ -1376,7 +1399,7 @@ void idle(void)
cmd_tokenize();
if (err_status == ERR_OK)
cmd_parser();
print_string("\n> ");
print_cmd_prompt();
}
}
@@ -1985,6 +2008,8 @@ void main(void)
check_and_flash_update_image();
syslog_init();
#ifdef DEBUG
// This register seems to work on the RTL8373 only if also the SDS
// Is correctly configured. Therefore, we can test it, here...
@@ -2031,12 +2056,13 @@ void main(void)
early_boot_handle_button();
execute_config();
print_string("\n> ");
print_cmd_prompt();
idle_ready = 1;
set_sys_led_state(SYS_LED_ON);
cmd_editor_init();
while (1) {
cmd_edit();
idle(); // Enter Idle mode until interrupt occurs
+105
View File
@@ -0,0 +1,105 @@
#include "machine.h"
#include "syslog.h"
#include "uip/uip.h"
#include "rtl837x_common.h"
#pragma codeseg BANK2
#pragma constseg BANK2
#define SYSLOG_P ((__xdata uint8_t *)uip_appdata)
__xdata char logbuf[LOGBUF_SIZE];
__xdata struct syslog_state syslog_state;
__xdata uip_ipaddr_t server_ip;
#define state syslog_state
void syslog_init(void) __banked
{
state.enabled = 0;
state.syslog_conn = 0;
state.writeptr = 0;
state.readptr = 0;
state.line_available = 0;
state.server_ip[0] = 0; state.server_ip[1] = 0; state.server_ip[2] = 0; state.server_ip[3] = 0;// Default to 0.0.0.0
}
void syslog_start(void) __banked
{
if (state.syslog_conn == 0) {
uip_ipaddr(server_ip, state.server_ip[0], state.server_ip[1], state.server_ip[2], state.server_ip[3]);
state.syslog_conn = uip_udp_new(&server_ip, HTONS(514));
if (state.syslog_conn == 0) {
print_string_no_syslog("Failed to create a new UDP client\n");
return;
}
print_string_no_syslog("Started syslog to IP ");
itoa(state.server_ip[0]); write_char('.'); itoa(state.server_ip[1]); write_char('.');
itoa(state.server_ip[2]); write_char('.'); itoa(state.server_ip[3]); write_char('\n');
state.enabled = 1;
}
else {
print_string_no_syslog("Syslog is already running\n");
}
}
void syslog_stop(void) __banked
{
state.enabled = 0;
if (state.syslog_conn != 0) {
uip_udp_remove(state.syslog_conn);
state.syslog_conn = 0;
print_string_no_syslog("Stopped syslog\n");
} else {
print_string_no_syslog("Syslog is not running\n");
}
}
void syslog_callback(uint16_t lport) __banked
{
if (lport != state.syslog_conn->lport)
return;
if ((state.readptr != state.writeptr) && state.line_available)
{
int16_t log_size = state.writeptr - state.readptr;
if (log_size < 0)
log_size += LOGBUF_SIZE;
// Skipping linefeeds at the start of the log line
uint16_t log_start = state.readptr;
while (log_size > 0 && logbuf[log_start] == '\n') {
log_start = (log_start + 1) & (LOGBUF_SIZE - 1);
log_size--;
}
// Skipping linefeeds and whitespaces at the end of the log line
uint16_t log_end = state.writeptr;
while ( (log_size > 0) &&
((logbuf[(log_end-1) & (LOGBUF_SIZE - 1)] == '\n') ||
(logbuf[(log_end-1) & (LOGBUF_SIZE - 1)] == ' ')))
{
log_end = (log_end - 1) & (LOGBUF_SIZE - 1);
log_size--;
}
if (log_size == 0) {
state.readptr = state.writeptr;
state.line_available = 0;
return;
}
memcpyc(SYSLOG_P, "<14>", 4); // Syslog priority prefix
if (log_end < log_start) {
memcpy(SYSLOG_P + 4, logbuf + log_start, LOGBUF_SIZE - log_start);
memcpy(SYSLOG_P + 4 + LOGBUF_SIZE - log_start, logbuf, log_end);
} else {
memcpy(SYSLOG_P + 4, logbuf + log_start, log_end - log_start);
}
uip_udp_send(log_size+4);
state.readptr = state.writeptr;
state.line_available = 0;
}
}
+26
View File
@@ -0,0 +1,26 @@
#ifndef _SYSLOG_H_
#define _SYSLOG_H_
#include <stdint.h>
#define LOGBUF_SIZE 512
struct syslog_state {
uint8_t enabled;
uint8_t line_available;
uint16_t writeptr ;
uint16_t readptr;
uint8_t server_ip[4];
struct uip_udp_conn *syslog_conn;
};
extern __xdata struct syslog_state syslog_state;
extern __xdata char logbuf[LOGBUF_SIZE];
void syslog_init(void) __banked;
void syslog_start(void) __banked;
void syslog_stop(void) __banked;
void syslog_callback(uint16_t lport) __banked;
#endif
+9
View File
@@ -0,0 +1,9 @@
#include "uip/uip.h"
#include "udp_apps.h"
void udp_callbacks(void)
{
dhcp_callback(uip_udp_conn->lport); // let the application decide if this is for it or not
syslog_callback(uip_udp_conn->lport); // let the application decide if this is for it or not
}
+13
View File
@@ -0,0 +1,13 @@
#ifndef _UDPAPPS_H_
#define _UDPAPPS_H_
#include "dhcp.h"
#include "syslog.h"
void udp_callbacks(void);
#ifndef UIP_UDP_APPCALL
#define UIP_UDP_APPCALL udp_callbacks
#endif /* UIP_UDP_APPCALL */
#endif
+1 -1
View File
@@ -153,7 +153,7 @@ typedef unsigned short uip_stats_t;
our project. */
/*#include "smtp.h"*/
#include "httpd.h"
#include "dhcp.h"
#include "udp_apps.h"
/*#include "telnetd.h"*/
/*#include "webserver.h" */
/*#include "dhcpc.h"*/
+1 -1
View File
@@ -234,7 +234,7 @@ __xdata struct uip_stats uip_stat;
#endif /* UIP_STATISTICS == 1 */
#if UIP_LOGGING == 1
#define UIP_LOG(m) print_string(m)
#define UIP_LOG(m) print_string_no_syslog(m);
#else
#define UIP_LOG(m)
#endif /* UIP_LOGGING == 1 */