PSTATE_MAP_L3,
};
+/* These values are exported via ubus and backwards compability
+ * needs to be kept!
+ */
+enum {
+ RAMODE_MAP_UNKNOWN = -1,
+ RAMODE_MAP_MANUAL,
+ RAMODE_MAP_AT_INIT,
+ RAMODE_MAP_DYNAMIC,
+ RAMODE_MAP_DYNAMIC_SOS,
+};
+
static DSL_CPE_ThreadCtrl_t thread;
static struct ubus_context *ctx;
static struct blob_buf b;
blobmsg_close_array(&b, c);
}
+static inline void m_array_u16(const char *id, const uint16_t *value, size_t len) {
+ void *c = blobmsg_open_array(&b, id);
+
+ for (size_t i = 0; i < len; ++i)
+ blobmsg_add_u16(&b, "", value[i]);
+
+ blobmsg_close_array(&b, c);
+}
+
static void m_vendor(const char *id, const uint8_t *value) {
// ITU-T T.35: U.S.
if (U16(value[0], value[1]) != 0xb500)
m_array("serial", out.data.SerialNumber, DSL_G997_LI_MAXLEN_SERIAL);
}
+static void pilot_tones_status(int fd) {
+#ifndef INCLUDE_DSL_CPE_API_DANUBE
+ IOCTL(DSL_PilotTonesStatus_t, DSL_FIO_PILOT_TONES_STATUS_GET);
+
+ m_array_u16("pilot_tones", out.data.nPilotTone, out.data.nNumData);
+#endif
+}
+
+static void band_border_status(int fd, DSL_AccessDir_t direction) {
+ IOCTL(DSL_BandBorderStatus_t, DSL_FIO_BAND_BORDER_STATUS_GET);
+
+ void *c, *c2;
+
+ c = blobmsg_open_array(&b, "limits");
+
+ for (size_t i = 0; i < out.data.nNumData; i++) {
+ c2 = blobmsg_open_table(&b, "");
+ blobmsg_add_u16(&b, "first", out.data.nBandLimits[i].nFirstToneIndex);
+ blobmsg_add_u16(&b, "last", out.data.nBandLimits[i].nLastToneIndex);
+ blobmsg_close_table(&b, c2);
+ }
+
+ blobmsg_close_array(&b, c);
+}
+
static void g977_get_bit_allocation(int fd, DSL_AccessDir_t direction) {
IOCTL_DIR(DSL_G997_BitAllocationNsc_t, DSL_FIO_G997_BIT_ALLOCATION_NSC_GET, direction);
#endif
}
-static void line_feature_config(int fd, DSL_AccessDir_t direction) {
+static void line_feature_config(int fd, DSL_AccessDir_t direction, bool *retx) {
IOCTL_DIR(DSL_LineFeature_t, DSL_FIO_LINE_FEATURE_STATUS_GET, direction)
m_bool("trellis", out.data.bTrellisEnable);
m_bool("bitswap", out.data.bBitswapEnable);
m_bool("retx", out.data.bReTxEnable);
m_bool("virtual_noise", out.data.bVirtualNoiseSupport);
+
+ *retx = out.data.bReTxEnable;
+}
+
+static void g997_rate_adaptation_status(int fd, DSL_AccessDir_t direction) {
+#ifndef INCLUDE_DSL_CPE_API_DANUBE
+ IOCTL_DIR(DSL_G997_RateAdaptationStatus_t, DSL_FIO_G997_RATE_ADAPTATION_STATUS_GET, direction);
+
+ int map = RAMODE_MAP_UNKNOWN;
+ const char *str;
+ switch (out.data.RA_MODE) {
+ STR_CASE_MAP(DSL_G997_RA_MODE_MANUAL, "Manual", RAMODE_MAP_MANUAL)
+ STR_CASE_MAP(DSL_G997_RA_MODE_AT_INIT, "At initialization", RAMODE_MAP_AT_INIT)
+ STR_CASE_MAP(DSL_G997_RA_MODE_DYNAMIC, "Dynamic", RAMODE_MAP_DYNAMIC)
+ STR_CASE_MAP(DSL_G997_RA_MODE_DYNAMIC_SOS, "Dynamic with SOS", RAMODE_MAP_DYNAMIC_SOS)
+ default:
+ str = NULL;
+ break;
+ };
+
+ if (str)
+ m_str("ra_mode", str);
+
+ if (map != PSTATE_MAP_UNKNOWN)
+ m_u32("ra_mode_num", map);
+#endif
}
static void g997_channel_status(int fd, DSL_AccessDir_t direction) {
IOCTL_DIR(DSL_G997_ChannelStatus_t, DSL_FIO_G997_CHANNEL_STATUS_GET, direction);
m_u32("interleave_delay", out.data.ActualInterleaveDelay * 10);
+ m_double("inp", (double)out.data.ActualImpulseNoiseProtection / 10);
#ifndef INCLUDE_DSL_CPE_API_DANUBE
// prefer ACTNDR, see comments in drv_dsl_cpe_api_g997.h
m_u32("data_rate", out.data.ActualNetDataRate);
m_u32("attndr", out.data.ATTNDR);
}
+static void pm_retx_counters_showtime(int fd, DSL_XTUDir_t direction) {
+#ifdef INCLUDE_DSL_CPE_PM_RETX_COUNTERS
+ IOCTL_DIR(DSL_PM_ReTxCounters_t, DSL_FIO_PM_RETX_COUNTERS_SHOWTIME_GET, direction);
+
+ m_u32("mineftr", out.data.nEftrMin);
+#endif
+}
+
+#ifndef INCLUDE_DSL_CPE_API_DANUBE
+static void olr_statistics(int fd, DSL_AccessDir_t direction) {
+ IOCTL_DIR(DSL_OlrStatistics_t, DSL_FIO_OLR_STATISTICS_GET, direction)
+
+ void *c = blobmsg_open_table(&b, "bitswap");
+ m_u32("requested", out.data.nBitswapRequested + out.data.nBitswapRequested);
+ m_u32("executed", out.data.nBitswapExecuted);
+ m_u32("rejected", out.data.nBitswapRejected);
+ m_u32("timeout", out.data.nBitswapTimeout);
+ blobmsg_close_table(&b, c);
+
+ c = blobmsg_open_table(&b, "sra");
+ m_u32("requested", out.data.nSraRequested);
+ m_u32("executed", out.data.nSraExecuted);
+ m_u32("rejected", out.data.nSraRejected);
+ m_u32("timeout", out.data.nSraTimeout);
+ blobmsg_close_table(&b, c);
+
+ c = blobmsg_open_table(&b, "sos");
+ m_u32("requested", out.data.nSosRequested);
+ m_u32("executed", out.data.nSosExecuted);
+ m_u32("rejected", out.data.nSosRejected);
+ m_u32("timeout", out.data.nSosTimeout);
+ blobmsg_close_table(&b, c);
+}
+#endif
+
static void pm_line_sec_counters_total(int fd, DSL_XTUDir_t direction) {
IOCTL_DIR(DSL_PM_LineSecCountersTotal_t, DSL_FIO_PM_LINE_SEC_COUNTERS_TOTAL_GET, direction)
#endif
}
+static void pm_retx_counters_total(int fd, DSL_XTUDir_t direction) {
+#ifdef INCLUDE_DSL_CPE_PM_RETX_COUNTERS
+ IOCTL_DIR(DSL_PM_ReTxCountersTotal_t, DSL_FIO_PM_RETX_COUNTERS_TOTAL_GET, direction);
+
+ m_u32("leftrs", out.data.nLeftr);
+#endif
+}
+
+static void pm_channel_counters_total(int fd, DSL_XTUDir_t direction) {
+ IOCTL_DIR(DSL_PM_ChannelCountersTotal_t, DSL_FIO_PM_CHANNEL_COUNTERS_TOTAL_GET, direction);
+
+ m_u32("cv_c", out.data.nCodeViolations);
+ m_u32("fec_c", out.data.nFEC);
+}
+
static void pm_data_path_counters_total(int fd, DSL_XTUDir_t direction) {
IOCTL_DIR(DSL_PM_DataPathCountersTotal_t, DSL_FIO_PM_DATA_PATH_COUNTERS_TOTAL_GET, direction);
blob_buf_init(&b, 0);
+ pilot_tones_status(fd);
+
+ c = blobmsg_open_table(&b, "bands");
+ c2 = blobmsg_open_table(&b, "downstream");
+ band_border_status(fd, DSL_DOWNSTREAM);
+ blobmsg_close_table(&b, c2);
+ c2 = blobmsg_open_table(&b, "upstream");
+ band_border_status(fd, DSL_UPSTREAM);
+ blobmsg_close_table(&b, c2);
+ blobmsg_close_table(&b, c);
+
c = blobmsg_open_table(&b, "bits");
c2 = blobmsg_open_table(&b, "downstream");
g977_get_bit_allocation(fd, DSL_DOWNSTREAM);
standard_t standard = STD_UNKNOWN;
profile_t profile = PROFILE_UNKNOWN;
vector_t vector = VECTOR_UNKNOWN;
+ bool retx_up = false, retx_down = false;
#ifndef INCLUDE_DSL_CPE_API_DANUBE
fd = open(DSL_CPE_DEVICE_NAME "/0", O_RDWR, 0644);
default:
break;
};
- line_feature_config(fd, DSL_UPSTREAM);
+ line_feature_config(fd, DSL_UPSTREAM, &retx_up);
+ g997_rate_adaptation_status(fd, DSL_UPSTREAM);
g997_channel_status(fd, DSL_UPSTREAM);
g997_line_status(fd, DSL_UPSTREAM);
+ if (retx_up)
+ pm_retx_counters_showtime(fd, DSL_FAR_END);
blobmsg_close_table(&b, c);
c = blobmsg_open_table(&b, "downstream");
default:
break;
};
- line_feature_config(fd, DSL_DOWNSTREAM);
+ line_feature_config(fd, DSL_DOWNSTREAM, &retx_down);
+ g997_rate_adaptation_status(fd, DSL_DOWNSTREAM);
g997_channel_status(fd, DSL_DOWNSTREAM);
g997_line_status(fd, DSL_DOWNSTREAM);
+ if (retx_down)
+ pm_retx_counters_showtime(fd, DSL_NEAR_END);
+ blobmsg_close_table(&b, c);
+
+#ifndef INCLUDE_DSL_CPE_API_DANUBE
+ c = blobmsg_open_table(&b, "olr");
+ c2 = blobmsg_open_table(&b, "downstream");
+ olr_statistics(fd, DSL_DOWNSTREAM);
+ blobmsg_close_table(&b, c2);
+ c2 = blobmsg_open_table(&b, "upstream");
+ olr_statistics(fd, DSL_UPSTREAM);
+ blobmsg_close_table(&b, c2);
blobmsg_close_table(&b, c);
+#endif
c = blobmsg_open_table(&b, "errors");
c2 = blobmsg_open_table(&b, "near");
pm_line_sec_counters_total(fd, DSL_NEAR_END);
+ if (retx_down)
+ pm_retx_counters_total(fd, DSL_NEAR_END);
+ pm_channel_counters_total(fd, DSL_NEAR_END);
pm_data_path_counters_total(fd, DSL_NEAR_END);
retx_statistics(fd, DSL_NEAR_END);
blobmsg_close_table(&b, c2);
c2 = blobmsg_open_table(&b, "far");
pm_line_sec_counters_total(fd, DSL_FAR_END);
+ if (retx_up)
+ pm_retx_counters_total(fd, DSL_FAR_END);
+ pm_channel_counters_total(fd, DSL_FAR_END);
pm_data_path_counters_total(fd, DSL_FAR_END);
retx_statistics(fd, DSL_FAR_END);
blobmsg_close_table(&b, c2);