Libor Pechacek
2013-03-28 15:30:17 UTC
When there is a peer speaking PTPv1 in the network we want to silently ignore
the packets instead of flooding system log with error messages. At the same
time we still want to report malformed packets. For that we reuse standard
error numbers and do more fine-grained error reporting in packet processing
routines.
Signed-off-by: Libor Pechacek <***@suse.cz>
---
Finally got around to finishing the patch. Please review/comment on/ack.
msg.c | 93 ++++++++++++++++++++++++++++++------------------------------
msg.h | 7 +++++
pmc_common.c | 19 +++++++++++--
port.c | 17 +++++++++--
tlv.c | 7 +++--
5 files changed, 87 insertions(+), 56 deletions(-)
diff --git a/msg.c b/msg.c
index eefd359..5c1adb0 100644
--- a/msg.c
+++ b/msg.c
@@ -17,6 +17,7 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <arpa/inet.h>
+#include <errno.h>
#include <malloc.h>
#include <string.h>
#include <time.h>
@@ -90,7 +91,7 @@ int64_t net2host64(int64_t val)
static int hdr_post_recv(struct ptp_header *m)
{
if ((m->ver & VERSION_MASK) != VERSION)
- return -1;
+ return -EPROTO;
m->messageLength = ntohs(m->messageLength);
m->correction = net2host64(m->correction);
m->sourcePortIdentity.portNumber = ntohs(m->sourcePortIdentity.portNumber);
@@ -107,33 +108,6 @@ static int hdr_pre_send(struct ptp_header *m)
return 0;
}
-static char *msg_type_string(int type)
-{
- switch (type) {
- case SYNC:
- return "SYNC";
- case DELAY_REQ:
- return "DELAY_REQ";
- case PDELAY_REQ:
- return "PDELAY_REQ";
- case PDELAY_RESP:
- return "PDELAY_RESP";
- case FOLLOW_UP:
- return "FOLLOW_UP";
- case DELAY_RESP:
- return "DELAY_RESP";
- case PDELAY_RESP_FOLLOW_UP:
- return "PDELAY_RESP_FOLLOW_UP";
- case ANNOUNCE:
- return "ANNOUNCE";
- case SIGNALING:
- return "SIGNALING";
- case MANAGEMENT:
- return "MANAGEMENT";
- }
- return "unknown";
-}
-
static void port_id_post_recv(struct PortIdentity *pid)
{
pid->portNumber = ntohs(pid->portNumber);
@@ -146,7 +120,7 @@ static void port_id_pre_send(struct PortIdentity *pid)
static int suffix_post_recv(uint8_t *ptr, int len, struct tlv_extra *last)
{
- int cnt;
+ int cnt, err;
struct TLV *tlv;
if (!ptr)
@@ -157,18 +131,18 @@ static int suffix_post_recv(uint8_t *ptr, int len, struct tlv_extra *last)
tlv->type = ntohs(tlv->type);
tlv->length = ntohs(tlv->length);
if (tlv->length % 2) {
- return -1;
+ return -EBADMSG;
}
len -= sizeof(struct TLV);
ptr += sizeof(struct TLV);
if (tlv->length > len) {
- return -1;
+ return -EBADMSG;
}
len -= tlv->length;
ptr += tlv->length;
- if (tlv_post_recv(tlv, len ? NULL : last)) {
- return -1;
- }
+ err = tlv_post_recv(tlv, len ? NULL : last);
+ if (err)
+ return err;
}
return cnt;
}
@@ -251,14 +225,15 @@ void msg_get(struct ptp_message *m)
int msg_post_recv(struct ptp_message *m, int cnt)
{
- int pdulen, type;
+ int pdulen, type, err;
uint8_t *suffix = NULL;
if (cnt < sizeof(struct ptp_header))
- return -1;
+ return -EBADMSG;
- if (hdr_post_recv(&m->header))
- return -1;
+ err = hdr_post_recv(&m->header);
+ if (err)
+ return err;
type = msg_type(m);
@@ -294,11 +269,11 @@ int msg_post_recv(struct ptp_message *m, int cnt)
pdulen = sizeof(struct management_msg);
break;
default:
- return -1;
+ return -EBADMSG;
}
if (cnt < pdulen)
- return -1;
+ return -EBADMSG;
switch (type) {
case SYNC:
@@ -339,15 +314,12 @@ int msg_post_recv(struct ptp_message *m, int cnt)
break;
}
- if (msg_sots_missing(m)) {
- pr_err("received %s without timestamp", msg_type_string(type));
- return -1;
- }
+ if (msg_sots_missing(m))
+ return -ETIME;
m->tlv_count = suffix_post_recv(suffix, cnt - pdulen, &m->last_tlv);
- if (m->tlv_count == -1) {
- return -1;
- }
+ if (m->tlv_count < 0)
+ return m->tlv_count;
return 0;
}
@@ -405,6 +377,33 @@ int msg_pre_send(struct ptp_message *m)
return 0;
}
+char *msg_type_string(int type)
+{
+ switch (type) {
+ case SYNC:
+ return "SYNC";
+ case DELAY_REQ:
+ return "DELAY_REQ";
+ case PDELAY_REQ:
+ return "PDELAY_REQ";
+ case PDELAY_RESP:
+ return "PDELAY_RESP";
+ case FOLLOW_UP:
+ return "FOLLOW_UP";
+ case DELAY_RESP:
+ return "DELAY_RESP";
+ case PDELAY_RESP_FOLLOW_UP:
+ return "PDELAY_RESP_FOLLOW_UP";
+ case ANNOUNCE:
+ return "ANNOUNCE";
+ case SIGNALING:
+ return "SIGNALING";
+ case MANAGEMENT:
+ return "MANAGEMENT";
+ }
+ return "unknown";
+}
+
void msg_print(struct ptp_message *m, FILE *fp)
{
fprintf(fp,
diff --git a/msg.h b/msg.h
index 279f3e6..1fad5e9 100644
--- a/msg.h
+++ b/msg.h
@@ -295,6 +295,13 @@ int msg_pre_send(struct ptp_message *m);
/**
* Print messages for debugging purposes.
+ * @param type Value of the messageType field as returned by @ref msg_type().
+ * @return String describing the message type.
+ */
+char *msg_type_string(int type);
+
+/**
+ * Print messages for debugging purposes.
* @param m A message obtained using @ref msg_allocate().
* @param fp An open file pointer.
*/
diff --git a/pmc_common.c b/pmc_common.c
index ee88bda..6dbeaf7 100644
--- a/pmc_common.c
+++ b/pmc_common.c
@@ -17,6 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
+#include <errno.h>
#include <string.h>
#include <stdlib.h>
@@ -163,7 +164,7 @@ int pmc_send_get_action(struct pmc *pmc, int id)
struct ptp_message *pmc_recv(struct pmc *pmc)
{
struct ptp_message *msg;
- int cnt;
+ int cnt, err;
msg = msg_allocate();
if (!msg) {
@@ -176,8 +177,20 @@ struct ptp_message *pmc_recv(struct pmc *pmc)
if (cnt <= 0) {
pr_err("recv message failed");
goto failed;
- } else if (msg_post_recv(msg, cnt)) {
- pr_err("bad message");
+ }
+ err = msg_post_recv(msg, cnt);
+ if (err) {
+ switch (err) {
+ case -EBADMSG:
+ pr_err("bad message");
+ break;
+ case -ETIME:
+ pr_err("received %s without timestamp",
+ msg_type_string(msg_type(msg)));
+ break;
+ case -EPROTO:
+ pr_debug("ignoring message");
+ }
goto failed;
}
diff --git a/port.c b/port.c
index d922047..9bfbf33 100644
--- a/port.c
+++ b/port.c
@@ -1873,7 +1873,7 @@ enum fsm_event port_event(struct port *p, int fd_index)
{
enum fsm_event event = EV_NONE;
struct ptp_message *msg;
- int cnt, fd = p->fda.fd[fd_index];
+ int cnt, fd = p->fda.fd[fd_index], err;
switch (fd_index) {
case FD_ANNOUNCE_TIMER:
@@ -1918,8 +1918,19 @@ enum fsm_event port_event(struct port *p, int fd_index)
msg_put(msg);
return EV_FAULT_DETECTED;
}
- if (msg_post_recv(msg, cnt)) {
- pr_err("port %hu: bad message", portnum(p));
+ err = msg_post_recv(msg, cnt);
+ if (err) {
+ switch (err) {
+ case -EBADMSG:
+ pr_err("port %hu: bad message", portnum(p));
+ break;
+ case -ETIME:
+ pr_err("port %hu: received %s without timestamp",
+ portnum(p), msg_type_string(msg_type(msg)));
+ break;
+ case -EPROTO:
+ pr_debug("port %hu: ignoring message", portnum(p));
+ }
msg_put(msg);
return EV_NONE;
}
diff --git a/tlv.c b/tlv.c
index 9b9e420..ce72e4b 100644
--- a/tlv.c
+++ b/tlv.c
@@ -17,6 +17,7 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <arpa/inet.h>
+#include <errno.h>
#include <string.h>
#include "port.h"
@@ -171,7 +172,7 @@ static int mgt_post_recv(struct management_tlv *m, uint16_t data_len,
}
return 0;
bad_length:
- return -1;
+ return -EBADMSG;
}
static void mgt_pre_send(struct management_tlv *m, struct tlv_extra *extra)
@@ -260,7 +261,7 @@ static int org_post_recv(struct organization_tlv *org)
}
return 0;
bad_length:
- return -1;
+ return -EBADMSG;
}
static void org_pre_send(struct organization_tlv *org)
@@ -335,7 +336,7 @@ int tlv_post_recv(struct TLV *tlv, struct tlv_extra *extra)
}
return result;
bad_length:
- return -1;
+ return -EBADMSG;
}
void tlv_pre_send(struct TLV *tlv, struct tlv_extra *extra)
the packets instead of flooding system log with error messages. At the same
time we still want to report malformed packets. For that we reuse standard
error numbers and do more fine-grained error reporting in packet processing
routines.
Signed-off-by: Libor Pechacek <***@suse.cz>
---
Finally got around to finishing the patch. Please review/comment on/ack.
msg.c | 93 ++++++++++++++++++++++++++++++------------------------------
msg.h | 7 +++++
pmc_common.c | 19 +++++++++++--
port.c | 17 +++++++++--
tlv.c | 7 +++--
5 files changed, 87 insertions(+), 56 deletions(-)
diff --git a/msg.c b/msg.c
index eefd359..5c1adb0 100644
--- a/msg.c
+++ b/msg.c
@@ -17,6 +17,7 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <arpa/inet.h>
+#include <errno.h>
#include <malloc.h>
#include <string.h>
#include <time.h>
@@ -90,7 +91,7 @@ int64_t net2host64(int64_t val)
static int hdr_post_recv(struct ptp_header *m)
{
if ((m->ver & VERSION_MASK) != VERSION)
- return -1;
+ return -EPROTO;
m->messageLength = ntohs(m->messageLength);
m->correction = net2host64(m->correction);
m->sourcePortIdentity.portNumber = ntohs(m->sourcePortIdentity.portNumber);
@@ -107,33 +108,6 @@ static int hdr_pre_send(struct ptp_header *m)
return 0;
}
-static char *msg_type_string(int type)
-{
- switch (type) {
- case SYNC:
- return "SYNC";
- case DELAY_REQ:
- return "DELAY_REQ";
- case PDELAY_REQ:
- return "PDELAY_REQ";
- case PDELAY_RESP:
- return "PDELAY_RESP";
- case FOLLOW_UP:
- return "FOLLOW_UP";
- case DELAY_RESP:
- return "DELAY_RESP";
- case PDELAY_RESP_FOLLOW_UP:
- return "PDELAY_RESP_FOLLOW_UP";
- case ANNOUNCE:
- return "ANNOUNCE";
- case SIGNALING:
- return "SIGNALING";
- case MANAGEMENT:
- return "MANAGEMENT";
- }
- return "unknown";
-}
-
static void port_id_post_recv(struct PortIdentity *pid)
{
pid->portNumber = ntohs(pid->portNumber);
@@ -146,7 +120,7 @@ static void port_id_pre_send(struct PortIdentity *pid)
static int suffix_post_recv(uint8_t *ptr, int len, struct tlv_extra *last)
{
- int cnt;
+ int cnt, err;
struct TLV *tlv;
if (!ptr)
@@ -157,18 +131,18 @@ static int suffix_post_recv(uint8_t *ptr, int len, struct tlv_extra *last)
tlv->type = ntohs(tlv->type);
tlv->length = ntohs(tlv->length);
if (tlv->length % 2) {
- return -1;
+ return -EBADMSG;
}
len -= sizeof(struct TLV);
ptr += sizeof(struct TLV);
if (tlv->length > len) {
- return -1;
+ return -EBADMSG;
}
len -= tlv->length;
ptr += tlv->length;
- if (tlv_post_recv(tlv, len ? NULL : last)) {
- return -1;
- }
+ err = tlv_post_recv(tlv, len ? NULL : last);
+ if (err)
+ return err;
}
return cnt;
}
@@ -251,14 +225,15 @@ void msg_get(struct ptp_message *m)
int msg_post_recv(struct ptp_message *m, int cnt)
{
- int pdulen, type;
+ int pdulen, type, err;
uint8_t *suffix = NULL;
if (cnt < sizeof(struct ptp_header))
- return -1;
+ return -EBADMSG;
- if (hdr_post_recv(&m->header))
- return -1;
+ err = hdr_post_recv(&m->header);
+ if (err)
+ return err;
type = msg_type(m);
@@ -294,11 +269,11 @@ int msg_post_recv(struct ptp_message *m, int cnt)
pdulen = sizeof(struct management_msg);
break;
default:
- return -1;
+ return -EBADMSG;
}
if (cnt < pdulen)
- return -1;
+ return -EBADMSG;
switch (type) {
case SYNC:
@@ -339,15 +314,12 @@ int msg_post_recv(struct ptp_message *m, int cnt)
break;
}
- if (msg_sots_missing(m)) {
- pr_err("received %s without timestamp", msg_type_string(type));
- return -1;
- }
+ if (msg_sots_missing(m))
+ return -ETIME;
m->tlv_count = suffix_post_recv(suffix, cnt - pdulen, &m->last_tlv);
- if (m->tlv_count == -1) {
- return -1;
- }
+ if (m->tlv_count < 0)
+ return m->tlv_count;
return 0;
}
@@ -405,6 +377,33 @@ int msg_pre_send(struct ptp_message *m)
return 0;
}
+char *msg_type_string(int type)
+{
+ switch (type) {
+ case SYNC:
+ return "SYNC";
+ case DELAY_REQ:
+ return "DELAY_REQ";
+ case PDELAY_REQ:
+ return "PDELAY_REQ";
+ case PDELAY_RESP:
+ return "PDELAY_RESP";
+ case FOLLOW_UP:
+ return "FOLLOW_UP";
+ case DELAY_RESP:
+ return "DELAY_RESP";
+ case PDELAY_RESP_FOLLOW_UP:
+ return "PDELAY_RESP_FOLLOW_UP";
+ case ANNOUNCE:
+ return "ANNOUNCE";
+ case SIGNALING:
+ return "SIGNALING";
+ case MANAGEMENT:
+ return "MANAGEMENT";
+ }
+ return "unknown";
+}
+
void msg_print(struct ptp_message *m, FILE *fp)
{
fprintf(fp,
diff --git a/msg.h b/msg.h
index 279f3e6..1fad5e9 100644
--- a/msg.h
+++ b/msg.h
@@ -295,6 +295,13 @@ int msg_pre_send(struct ptp_message *m);
/**
* Print messages for debugging purposes.
+ * @param type Value of the messageType field as returned by @ref msg_type().
+ * @return String describing the message type.
+ */
+char *msg_type_string(int type);
+
+/**
+ * Print messages for debugging purposes.
* @param m A message obtained using @ref msg_allocate().
* @param fp An open file pointer.
*/
diff --git a/pmc_common.c b/pmc_common.c
index ee88bda..6dbeaf7 100644
--- a/pmc_common.c
+++ b/pmc_common.c
@@ -17,6 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
+#include <errno.h>
#include <string.h>
#include <stdlib.h>
@@ -163,7 +164,7 @@ int pmc_send_get_action(struct pmc *pmc, int id)
struct ptp_message *pmc_recv(struct pmc *pmc)
{
struct ptp_message *msg;
- int cnt;
+ int cnt, err;
msg = msg_allocate();
if (!msg) {
@@ -176,8 +177,20 @@ struct ptp_message *pmc_recv(struct pmc *pmc)
if (cnt <= 0) {
pr_err("recv message failed");
goto failed;
- } else if (msg_post_recv(msg, cnt)) {
- pr_err("bad message");
+ }
+ err = msg_post_recv(msg, cnt);
+ if (err) {
+ switch (err) {
+ case -EBADMSG:
+ pr_err("bad message");
+ break;
+ case -ETIME:
+ pr_err("received %s without timestamp",
+ msg_type_string(msg_type(msg)));
+ break;
+ case -EPROTO:
+ pr_debug("ignoring message");
+ }
goto failed;
}
diff --git a/port.c b/port.c
index d922047..9bfbf33 100644
--- a/port.c
+++ b/port.c
@@ -1873,7 +1873,7 @@ enum fsm_event port_event(struct port *p, int fd_index)
{
enum fsm_event event = EV_NONE;
struct ptp_message *msg;
- int cnt, fd = p->fda.fd[fd_index];
+ int cnt, fd = p->fda.fd[fd_index], err;
switch (fd_index) {
case FD_ANNOUNCE_TIMER:
@@ -1918,8 +1918,19 @@ enum fsm_event port_event(struct port *p, int fd_index)
msg_put(msg);
return EV_FAULT_DETECTED;
}
- if (msg_post_recv(msg, cnt)) {
- pr_err("port %hu: bad message", portnum(p));
+ err = msg_post_recv(msg, cnt);
+ if (err) {
+ switch (err) {
+ case -EBADMSG:
+ pr_err("port %hu: bad message", portnum(p));
+ break;
+ case -ETIME:
+ pr_err("port %hu: received %s without timestamp",
+ portnum(p), msg_type_string(msg_type(msg)));
+ break;
+ case -EPROTO:
+ pr_debug("port %hu: ignoring message", portnum(p));
+ }
msg_put(msg);
return EV_NONE;
}
diff --git a/tlv.c b/tlv.c
index 9b9e420..ce72e4b 100644
--- a/tlv.c
+++ b/tlv.c
@@ -17,6 +17,7 @@
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
#include <arpa/inet.h>
+#include <errno.h>
#include <string.h>
#include "port.h"
@@ -171,7 +172,7 @@ static int mgt_post_recv(struct management_tlv *m, uint16_t data_len,
}
return 0;
bad_length:
- return -1;
+ return -EBADMSG;
}
static void mgt_pre_send(struct management_tlv *m, struct tlv_extra *extra)
@@ -260,7 +261,7 @@ static int org_post_recv(struct organization_tlv *org)
}
return 0;
bad_length:
- return -1;
+ return -EBADMSG;
}
static void org_pre_send(struct organization_tlv *org)
@@ -335,7 +336,7 @@ int tlv_post_recv(struct TLV *tlv, struct tlv_extra *extra)
}
return result;
bad_length:
- return -1;
+ return -EBADMSG;
}
void tlv_pre_send(struct TLV *tlv, struct tlv_extra *extra)