kern/175759: Correct data types for fields of struct qm_trace{} from <sys/queue.h>

Andrey Simonenko simon at comsys.ntu-kpi.kiev.ua
Sat Feb 2 11:00:02 UTC 2013


The following reply was made to PR kern/175759; it has been noted by GNATS.

From: Andrey Simonenko <simon at comsys.ntu-kpi.kiev.ua>
To: Gleb Smirnoff <glebius at FreeBSD.org>
Cc: FreeBSD-gnats-submit at freebsd.org
Subject: Re: kern/175759: Correct data types for fields of struct qm_trace{}
 from <sys/queue.h>
Date: Sat, 2 Feb 2013 12:53:04 +0200

 What about the following change:
 
 1. Allow a user to specify how many places to remember via QMD_TRACE_N.
 
 2. Initialize struct qm_trace{} in *_INIT() and *_INITIALIZE().
 
 3. Lists' elements usually are not initialized, so first entry in
    the info[] array will have random index.
 
 4. struct qm_trace{} is not anonymous, to allow it to be used in
    debugger scripts.
 
 I chose "unsigned long" for line number, but "int" or "unsigned int"
 also can be used.
 
 --- queue.h.orig	2012-11-19 14:38:37.000000000 +0200
 +++ queue.h	2013-02-02 12:40:42.000000000 +0200
 @@ -103,38 +103,54 @@
   *
   */
  #ifdef QUEUE_MACRO_DEBUG
 -/* Store the last 2 places the queue element or head was altered */
 +
 +#ifndef QMD_TRACE_N
 +# define QMD_TRACE_N	2
 +#endif
 +
 +/* Store the last QMD_TRACE_N places the queue element or head was altered */
  struct qm_trace {
 -	char * lastfile;
 -	int lastline;
 -	char * prevfile;
 -	int prevline;
 +	unsigned int	idx;
 +	struct {
 +		const char	*file;
 +		unsigned long	line;
 +	}		info[QMD_TRACE_N];
  };
  
 -#define	TRACEBUF	struct qm_trace trace;
 -#define	TRASHIT(x)	do {(x) = (void *)-1;} while (0)
 +#define	QMD_TRACE_BUF	struct qm_trace trace;
 +#define	QMD_TRASHIT(x)	do {(x) = (void *)-1;} while (0)
  #define	QMD_SAVELINK(name, link)	void **name = (void *)&(link)
  
 -#define	QMD_TRACE_HEAD(head) do {					\
 -	(head)->trace.prevline = (head)->trace.lastline;		\
 -	(head)->trace.prevfile = (head)->trace.lastfile;		\
 -	(head)->trace.lastline = __LINE__;				\
 -	(head)->trace.lastfile = __FILE__;				\
 +#define	QMD_TRACE_INITIALIZER , { 0, { { __FILE__, __LINE__ } } }
 +
 +#define	QMD_TRACE_INIT(x) do {						\
 +	unsigned int __i;						\
 +	(x)->trace.idx = 0;						\
 +	(x)->trace.info[0].file = __FILE__;				\
 +	(x)->trace.info[0].line = __LINE__;				\
 +	for (__i = 1; __i < QMD_TRACE_N; ++__i) {			\
 +		(x)->trace.info[__i].file = NULL;			\
 +		(x)->trace.info[__i].line = 0;				\
 +	}								\
  } while (0)
  
 -#define	QMD_TRACE_ELEM(elem) do {					\
 -	(elem)->trace.prevline = (elem)->trace.lastline;		\
 -	(elem)->trace.prevfile = (elem)->trace.lastfile;		\
 -	(elem)->trace.lastline = __LINE__;				\
 -	(elem)->trace.lastfile = __FILE__;				\
 +#define	QMD_TRACE(x) do {						\
 +	(x)->trace.idx = ((x)->trace.idx + 1) % QMD_TRACE_N;		\
 +	(x)->trace.info[(x)->trace.idx].file = __FILE__;		\
 +	(x)->trace.info[(x)->trace.idx].line = __LINE__;		\
  } while (0)
  
 +#define QMD_TRACE_HEAD(head) QMD_TRACE(head)
 +#define QMD_TRACE_ELEM(elem) QMD_TRACE(elem)
 +
  #else
 +#define	QMD_TRACE_BUF
 +#define	QMD_TRACE_INITIALIZER
 +#define	QMD_TRACE_INIT(x)
  #define	QMD_TRACE_ELEM(elem)
  #define	QMD_TRACE_HEAD(head)
  #define	QMD_SAVELINK(name, link)
 -#define	TRACEBUF
 -#define	TRASHIT(x)
 +#define	QMD_TRASHIT(x)
  #endif	/* QUEUE_MACRO_DEBUG */
  
  /*
 @@ -202,7 +218,7 @@
  			curelm = SLIST_NEXT(curelm, field);		\
  		SLIST_REMOVE_AFTER(curelm, field);			\
  	}								\
 -	TRASHIT(*oldnext);						\
 +	QMD_TRASHIT(*oldnext);						\
  } while (0)
  
  #define SLIST_REMOVE_AFTER(elm, field) do {				\
 @@ -303,7 +319,7 @@
  			curelm = STAILQ_NEXT(curelm, field);		\
  		STAILQ_REMOVE_AFTER(head, curelm, field);		\
  	}								\
 -	TRASHIT(*oldnext);						\
 +	QMD_TRASHIT(*oldnext);						\
  } while (0)
  
  #define STAILQ_REMOVE_AFTER(head, elm, field) do {			\
 @@ -436,8 +452,8 @@
  		LIST_NEXT((elm), field)->field.le_prev = 		\
  		    (elm)->field.le_prev;				\
  	*(elm)->field.le_prev = LIST_NEXT((elm), field);		\
 -	TRASHIT(*oldnext);						\
 -	TRASHIT(*oldprev);						\
 +	QMD_TRASHIT(*oldnext);						\
 +	QMD_TRASHIT(*oldprev);						\
  } while (0)
  
  #define LIST_SWAP(head1, head2, type, field) do {			\
 @@ -457,17 +473,17 @@
  struct name {								\
  	struct type *tqh_first;	/* first element */			\
  	struct type **tqh_last;	/* addr of last next element */		\
 -	TRACEBUF							\
 +	QMD_TRACE_BUF							\
  }
  
  #define	TAILQ_HEAD_INITIALIZER(head)					\
 -	{ NULL, &(head).tqh_first }
 +	{ NULL, &(head).tqh_first QMD_TRACE_INITIALIZER }
  
  #define	TAILQ_ENTRY(type)						\
  struct {								\
  	struct type *tqe_next;	/* next element */			\
  	struct type **tqe_prev;	/* address of previous next element */	\
 -	TRACEBUF							\
 +	QMD_TRACE_BUF							\
  }
  
  /*
 @@ -542,7 +558,7 @@
  #define	TAILQ_INIT(head) do {						\
  	TAILQ_FIRST((head)) = NULL;					\
  	(head)->tqh_last = &TAILQ_FIRST((head));			\
 -	QMD_TRACE_HEAD(head);						\
 +	QMD_TRACE_INIT(head);						\
  } while (0)
  
  #define	TAILQ_INSERT_AFTER(head, listelm, elm, field) do {		\
 @@ -557,7 +573,7 @@
  	TAILQ_NEXT((listelm), field) = (elm);				\
  	(elm)->field.tqe_prev = &TAILQ_NEXT((listelm), field);		\
  	QMD_TRACE_ELEM(&(elm)->field);					\
 -	QMD_TRACE_ELEM(&listelm->field);				\
 +	QMD_TRACE_ELEM(&(listelm)->field);				\
  } while (0)
  
  #define	TAILQ_INSERT_BEFORE(listelm, elm, field) do {			\
 @@ -567,7 +583,7 @@
  	*(listelm)->field.tqe_prev = (elm);				\
  	(listelm)->field.tqe_prev = &TAILQ_NEXT((elm), field);		\
  	QMD_TRACE_ELEM(&(elm)->field);					\
 -	QMD_TRACE_ELEM(&listelm->field);				\
 +	QMD_TRACE_ELEM(&(listelm)->field);				\
  } while (0)
  
  #define	TAILQ_INSERT_HEAD(head, elm, field) do {			\
 @@ -614,8 +630,8 @@
  		QMD_TRACE_HEAD(head);					\
  	}								\
  	*(elm)->field.tqe_prev = TAILQ_NEXT((elm), field);		\
 -	TRASHIT(*oldnext);						\
 -	TRASHIT(*oldprev);						\
 +	QMD_TRASHIT(*oldnext);						\
 +	QMD_TRASHIT(*oldprev);						\
  	QMD_TRACE_ELEM(&(elm)->field);					\
  } while (0)
  
 @@ -634,6 +650,8 @@
  		swap_first->field.tqe_prev = &(head2)->tqh_first;	\
  	else								\
  		(head2)->tqh_last = &(head2)->tqh_first;		\
 +	QMD_TRACE_HEAD(head1);						\
 +	QMD_TRACE_HEAD(head2);						\
  } while (0)
  
  #endif /* !_SYS_QUEUE_H_ */


More information about the freebsd-bugs mailing list