2015-06-03 18:26:19 +08:00
|
|
|
#include <generated/csr.h>
|
|
|
|
|
|
|
|
#include <lwip/init.h>
|
|
|
|
#include <lwip/memp.h>
|
|
|
|
#include <lwip/ip4_addr.h>
|
|
|
|
#include <lwip/ip4.h>
|
|
|
|
#include <lwip/netif.h>
|
|
|
|
#include <lwip/sys.h>
|
|
|
|
#include <lwip/udp.h>
|
|
|
|
#include <lwip/timers.h>
|
|
|
|
|
|
|
|
#include "log.h"
|
|
|
|
#include "moninj.h"
|
|
|
|
|
|
|
|
enum {
|
2015-06-06 00:03:30 +08:00
|
|
|
MONINJ_REQ_MONITOR = 1,
|
|
|
|
MONINJ_REQ_TTLSET = 2
|
2015-06-03 18:26:19 +08:00
|
|
|
};
|
|
|
|
|
2015-06-09 19:51:02 +08:00
|
|
|
enum {
|
|
|
|
MONINJ_TTL_MODE_EXP = 0,
|
|
|
|
MONINJ_TTL_MODE_1 = 1,
|
|
|
|
MONINJ_TTL_MODE_0 = 2,
|
|
|
|
MONINJ_TTL_MODE_IN = 3
|
|
|
|
};
|
|
|
|
|
|
|
|
enum {
|
|
|
|
MONINJ_TTL_OVERRIDE_ENABLE = 0,
|
|
|
|
MONINJ_TTL_OVERRIDE_O = 1,
|
|
|
|
MONINJ_TTL_OVERRIDE_OE = 2
|
|
|
|
};
|
|
|
|
|
2015-06-03 18:26:19 +08:00
|
|
|
static struct udp_pcb *listen_pcb;
|
|
|
|
|
|
|
|
struct monitor_reply {
|
|
|
|
long long int ttl_levels;
|
|
|
|
long long int ttl_oes;
|
2015-06-06 00:03:30 +08:00
|
|
|
long long int ttl_overrides;
|
2015-12-04 15:57:39 +08:00
|
|
|
unsigned int dds_ftws[CONFIG_DDS_CHANNEL_COUNT];
|
2015-06-03 18:26:19 +08:00
|
|
|
};
|
|
|
|
|
|
|
|
static void moninj_monitor(const ip_addr_t *addr, u16_t port)
|
|
|
|
{
|
|
|
|
struct monitor_reply reply;
|
|
|
|
int i;
|
|
|
|
struct pbuf *reply_p;
|
|
|
|
|
|
|
|
reply.ttl_levels = 0;
|
|
|
|
reply.ttl_oes = 0;
|
2015-06-09 19:51:02 +08:00
|
|
|
reply.ttl_overrides = 0;
|
2015-12-04 15:57:39 +08:00
|
|
|
for(i=0;i<CONFIG_RTIO_REGULAR_TTL_COUNT;i++) {
|
2015-06-09 19:51:02 +08:00
|
|
|
rtio_moninj_mon_chan_sel_write(i);
|
|
|
|
rtio_moninj_mon_probe_sel_write(0);
|
2015-06-20 05:30:17 +08:00
|
|
|
rtio_moninj_mon_value_update_write(1);
|
2015-06-09 19:51:02 +08:00
|
|
|
if(rtio_moninj_mon_value_read())
|
2015-06-03 18:26:19 +08:00
|
|
|
reply.ttl_levels |= 1LL << i;
|
2015-06-09 19:51:02 +08:00
|
|
|
rtio_moninj_mon_probe_sel_write(1);
|
2015-06-20 05:30:17 +08:00
|
|
|
rtio_moninj_mon_value_update_write(1);
|
2015-06-09 19:51:02 +08:00
|
|
|
if(rtio_moninj_mon_value_read())
|
2015-06-03 18:26:19 +08:00
|
|
|
reply.ttl_oes |= 1LL << i;
|
2015-06-09 19:51:02 +08:00
|
|
|
rtio_moninj_inj_chan_sel_write(i);
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_ENABLE);
|
|
|
|
if(rtio_moninj_inj_value_read())
|
|
|
|
reply.ttl_overrides |= 1LL << i;
|
2015-06-03 18:26:19 +08:00
|
|
|
}
|
|
|
|
|
2015-12-04 15:57:39 +08:00
|
|
|
rtio_moninj_mon_chan_sel_write(CONFIG_RTIO_DDS_CHANNEL);
|
|
|
|
for(i=0;i<CONFIG_DDS_CHANNEL_COUNT;i++) {
|
2015-06-20 05:30:17 +08:00
|
|
|
rtio_moninj_mon_probe_sel_write(i);
|
|
|
|
rtio_moninj_mon_value_update_write(1);
|
|
|
|
reply.dds_ftws[i] = rtio_moninj_mon_value_read();
|
|
|
|
}
|
|
|
|
|
2015-06-03 18:26:19 +08:00
|
|
|
reply_p = pbuf_alloc(PBUF_TRANSPORT, sizeof(struct monitor_reply), PBUF_RAM);
|
|
|
|
if(!reply_p) {
|
2016-02-15 06:54:54 +08:00
|
|
|
core_log("Failed to allocate pbuf for monitor reply\n");
|
2015-06-03 18:26:19 +08:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
memcpy(reply_p->payload, &reply, sizeof(struct monitor_reply));
|
|
|
|
udp_sendto(listen_pcb, reply_p, addr, port);
|
|
|
|
pbuf_free(reply_p);
|
|
|
|
}
|
|
|
|
|
2015-06-06 00:03:30 +08:00
|
|
|
static void moninj_ttlset(int channel, int mode)
|
|
|
|
{
|
2015-06-09 19:51:02 +08:00
|
|
|
rtio_moninj_inj_chan_sel_write(channel);
|
|
|
|
switch(mode) {
|
|
|
|
case MONINJ_TTL_MODE_EXP:
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_ENABLE);
|
|
|
|
rtio_moninj_inj_value_write(0);
|
|
|
|
break;
|
|
|
|
case MONINJ_TTL_MODE_1:
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_O);
|
|
|
|
rtio_moninj_inj_value_write(1);
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_OE);
|
|
|
|
rtio_moninj_inj_value_write(1);
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_ENABLE);
|
|
|
|
rtio_moninj_inj_value_write(1);
|
|
|
|
break;
|
|
|
|
case MONINJ_TTL_MODE_0:
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_O);
|
|
|
|
rtio_moninj_inj_value_write(0);
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_OE);
|
|
|
|
rtio_moninj_inj_value_write(1);
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_ENABLE);
|
|
|
|
rtio_moninj_inj_value_write(1);
|
|
|
|
break;
|
|
|
|
case MONINJ_TTL_MODE_IN:
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_OE);
|
|
|
|
rtio_moninj_inj_value_write(0);
|
|
|
|
rtio_moninj_inj_override_sel_write(MONINJ_TTL_OVERRIDE_ENABLE);
|
|
|
|
rtio_moninj_inj_value_write(1);
|
|
|
|
break;
|
|
|
|
default:
|
2016-02-15 06:54:54 +08:00
|
|
|
core_log("unknown TTL mode %d\n", mode);
|
2015-06-09 19:51:02 +08:00
|
|
|
break;
|
|
|
|
}
|
2015-06-06 00:03:30 +08:00
|
|
|
}
|
|
|
|
|
2015-06-03 18:26:19 +08:00
|
|
|
static void moninj_recv(void *arg, struct udp_pcb *upcb, struct pbuf *req,
|
|
|
|
const ip_addr_t *addr, u16_t port)
|
|
|
|
{
|
2015-06-06 00:03:30 +08:00
|
|
|
char *p = (char *)req->payload;
|
|
|
|
|
2015-06-03 18:26:19 +08:00
|
|
|
if(req->len >= 1) {
|
2015-06-06 00:03:30 +08:00
|
|
|
switch(p[0]) {
|
2015-06-03 18:26:19 +08:00
|
|
|
case MONINJ_REQ_MONITOR:
|
|
|
|
moninj_monitor(addr, port);
|
|
|
|
break;
|
2015-06-06 00:03:30 +08:00
|
|
|
case MONINJ_REQ_TTLSET:
|
|
|
|
if(req->len < 3)
|
|
|
|
break;
|
|
|
|
moninj_ttlset(p[1], p[2]);
|
|
|
|
break;
|
2015-06-03 18:26:19 +08:00
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
pbuf_free(req); /* beware: addr may point into the req pbuf */
|
|
|
|
}
|
|
|
|
|
|
|
|
void moninj_init(void)
|
|
|
|
{
|
|
|
|
listen_pcb = udp_new();
|
|
|
|
if(!listen_pcb) {
|
2016-02-15 06:54:54 +08:00
|
|
|
core_log("Failed to create UDP listening PCB\n");
|
2015-06-03 18:26:19 +08:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
udp_bind(listen_pcb, IP_ADDR_ANY, 3250);
|
|
|
|
udp_recv(listen_pcb, moninj_recv, NULL);
|
|
|
|
}
|