packet: turn tunnel lock into spinlock

Lock is only held to update/check ints, so spin lock will be more
efficient.

Place the member of Packet in a new "persistent" area to make it
clear this is not touched by the PacketReinit logic.

Ticket: #5592.
pull/8085/head
Victor Julien 2 years ago
parent 57e70841c4
commit 1fafb83fed

@ -617,11 +617,6 @@ typedef struct Packet_
* It should always point to the lowest
* packet in a encapsulated packet */
/** mutex to protect access to:
* - tunnel_rtv_cnt
* - tunnel_tpr_cnt
*/
SCMutex tunnel_mutex;
/* ready to set verdict counter, only set in root */
uint16_t tunnel_rtv_cnt;
/* tunnel packet ref count */
@ -638,6 +633,16 @@ typedef struct Packet_
#ifdef PROFILING
PktProfiling *profile;
#endif
/* things in the packet that live beyond a reinit */
struct {
/** lock to protect access to:
* - tunnel_rtv_cnt
* - tunnel_tpr_cnt
* - nfq_v.mark
* - flags
*/
SCSpinlock tunnel_lock;
} persistent;
} Packet;
/** highest mtu of the interfaces we monitor */
@ -773,11 +778,13 @@ void CaptureStatsSetup(ThreadVars *tv, CaptureStats *s);
((p)->root ? (p)->root->tunnel_rtv_cnt++ : (p)->tunnel_rtv_cnt++); \
} while (0)
#define TUNNEL_INCR_PKT_TPR(p) do { \
SCMutexLock((p)->root ? &(p)->root->tunnel_mutex : &(p)->tunnel_mutex); \
((p)->root ? (p)->root->tunnel_tpr_cnt++ : (p)->tunnel_tpr_cnt++); \
SCMutexUnlock((p)->root ? &(p)->root->tunnel_mutex : &(p)->tunnel_mutex); \
} while (0)
static inline void TUNNEL_INCR_PKT_TPR(Packet *p)
{
Packet *rp = p->root ? p->root : p;
SCSpinLock(&rp->persistent.tunnel_lock);
rp->tunnel_tpr_cnt++;
SCSpinUnlock(&rp->persistent.tunnel_lock);
}
#define TUNNEL_PKT_RTV(p) ((p)->root ? (p)->root->tunnel_rtv_cnt : (p)->tunnel_rtv_cnt)
#define TUNNEL_PKT_TPR(p) ((p)->root ? (p)->root->tunnel_tpr_cnt : (p)->tunnel_tpr_cnt)
@ -1093,8 +1100,8 @@ static inline void DecodeSetNoPacketInspectionFlag(Packet *p)
static inline bool VerdictTunnelPacket(Packet *p)
{
bool verdict = true;
SCMutex *m = p->root ? &p->root->tunnel_mutex : &p->tunnel_mutex;
SCMutexLock(m);
SCSpinlock *lock = p->root ? &p->root->persistent.tunnel_lock : &p->persistent.tunnel_lock;
SCSpinLock(lock);
const uint16_t outstanding = TUNNEL_PKT_TPR(p) - TUNNEL_PKT_RTV(p);
SCLogDebug("tunnel: outstanding %u", outstanding);
@ -1108,7 +1115,7 @@ static inline bool VerdictTunnelPacket(Packet *p)
} else {
verdict = false;
}
SCMutexUnlock(m);
SCSpinUnlock(lock);
return verdict;
}

@ -233,11 +233,11 @@ static int DetectMarkPacket(DetectEngineThreadCtx *det_ctx, Packet *p,
* are fine. */
if (p->flags & PKT_REBUILT_FRAGMENT) {
Packet *tp = p->root ? p->root : p;
SCMutexLock(&tp->tunnel_mutex);
SCSpinLock(&tp->persistent.tunnel_lock);
tp->nfq_v.mark = (nf_data->mark & nf_data->mask)
| (tp->nfq_v.mark & ~(nf_data->mask));
tp->flags |= PKT_MARK_MODIFIED;
SCMutexUnlock(&tp->tunnel_mutex);
SCSpinUnlock(&tp->persistent.tunnel_lock);
}
}
}

@ -60,7 +60,7 @@ bool PacketCheckAction(const Packet *p, const uint8_t a)
*/
void PacketInit(Packet *p)
{
SCMutexInit(&p->tunnel_mutex, NULL);
SCSpinInit(&p->persistent.tunnel_lock, 0);
p->alerts.alerts = PacketAlertCreate();
PACKET_RESET_CHECKSUMS(p);
p->livedev = NULL;
@ -181,7 +181,7 @@ void PacketDestructor(Packet *p)
}
PacketAlertFree(p->alerts.alerts);
PACKET_FREE_EXTDATA(p);
SCMutexDestroy(&p->tunnel_mutex);
SCSpinDestroy(&p->persistent.tunnel_lock);
AppLayerDecoderEventsFreeEvents(&p->app_layer_events);
PACKET_PROFILING_RESET(p);
}

@ -496,11 +496,11 @@ static int NFQBypassCallback(Packet *p)
* work for those. Rebuilt packets from IP fragments are fine. */
if (p->flags & PKT_REBUILT_FRAGMENT) {
Packet *tp = p->root ? p->root : p;
SCMutexLock(&tp->tunnel_mutex);
SCSpinLock(&tp->persistent.tunnel_lock);
tp->nfq_v.mark = (nfq_config.bypass_mark & nfq_config.bypass_mask)
| (tp->nfq_v.mark & ~nfq_config.bypass_mask);
tp->flags |= PKT_MARK_MODIFIED;
SCMutexUnlock(&tp->tunnel_mutex);
SCSpinUnlock(&tp->persistent.tunnel_lock);
return 1;
}
return 0;

@ -365,8 +365,8 @@ void TmqhOutputPacketpool(ThreadVars *t, Packet *p)
p,p->root ? "upper layer" : "tunnel root");
/* get a lock to access root packet fields */
SCMutex *m = p->root ? &p->root->tunnel_mutex : &p->tunnel_mutex;
SCMutexLock(m);
SCSpinlock *lock = p->root ? &p->root->persistent.tunnel_lock : &p->persistent.tunnel_lock;
SCSpinLock(lock);
if (IS_TUNNEL_ROOT_PKT(p)) {
SCLogDebug("IS_TUNNEL_ROOT_PKT == TRUE");
@ -390,7 +390,7 @@ void TmqhOutputPacketpool(ThreadVars *t, Packet *p)
SET_TUNNEL_PKT_VERDICTED(p);
PACKET_PROFILING_END(p);
SCMutexUnlock(m);
SCSpinUnlock(lock);
SCReturn;
}
} else {
@ -426,7 +426,7 @@ void TmqhOutputPacketpool(ThreadVars *t, Packet *p)
/* fall through */
}
}
SCMutexUnlock(m);
SCSpinUnlock(lock);
SCLogDebug("tunnel stuff done, move on (proot %d)", proot);
}

Loading…
Cancel
Save