|
@@ -2847,6 +2847,18 @@ static inline int skb_linearize_cow(struct sk_buff *skb)
|
|
|
__skb_linearize(skb) : 0;
|
|
|
}
|
|
|
|
|
|
+static __always_inline void
|
|
|
+__skb_postpull_rcsum(struct sk_buff *skb, const void *start, unsigned int len,
|
|
|
+ unsigned int off)
|
|
|
+{
|
|
|
+ if (skb->ip_summed == CHECKSUM_COMPLETE)
|
|
|
+ skb->csum = csum_block_sub(skb->csum,
|
|
|
+ csum_partial(start, len, 0), off);
|
|
|
+ else if (skb->ip_summed == CHECKSUM_PARTIAL &&
|
|
|
+ skb_checksum_start_offset(skb) < 0)
|
|
|
+ skb->ip_summed = CHECKSUM_NONE;
|
|
|
+}
|
|
|
+
|
|
|
/**
|
|
|
* skb_postpull_rcsum - update checksum for received skb after pull
|
|
|
* @skb: buffer to update
|
|
@@ -2857,36 +2869,38 @@ static inline int skb_linearize_cow(struct sk_buff *skb)
|
|
|
* update the CHECKSUM_COMPLETE checksum, or set ip_summed to
|
|
|
* CHECKSUM_NONE so that it can be recomputed from scratch.
|
|
|
*/
|
|
|
-
|
|
|
static inline void skb_postpull_rcsum(struct sk_buff *skb,
|
|
|
const void *start, unsigned int len)
|
|
|
{
|
|
|
- if (skb->ip_summed == CHECKSUM_COMPLETE)
|
|
|
- skb->csum = csum_sub(skb->csum, csum_partial(start, len, 0));
|
|
|
- else if (skb->ip_summed == CHECKSUM_PARTIAL &&
|
|
|
- skb_checksum_start_offset(skb) < 0)
|
|
|
- skb->ip_summed = CHECKSUM_NONE;
|
|
|
+ __skb_postpull_rcsum(skb, start, len, 0);
|
|
|
}
|
|
|
|
|
|
-unsigned char *skb_pull_rcsum(struct sk_buff *skb, unsigned int len);
|
|
|
+static __always_inline void
|
|
|
+__skb_postpush_rcsum(struct sk_buff *skb, const void *start, unsigned int len,
|
|
|
+ unsigned int off)
|
|
|
+{
|
|
|
+ if (skb->ip_summed == CHECKSUM_COMPLETE)
|
|
|
+ skb->csum = csum_block_add(skb->csum,
|
|
|
+ csum_partial(start, len, 0), off);
|
|
|
+}
|
|
|
|
|
|
+/**
|
|
|
+ * skb_postpush_rcsum - update checksum for received skb after push
|
|
|
+ * @skb: buffer to update
|
|
|
+ * @start: start of data after push
|
|
|
+ * @len: length of data pushed
|
|
|
+ *
|
|
|
+ * After doing a push on a received packet, you need to call this to
|
|
|
+ * update the CHECKSUM_COMPLETE checksum.
|
|
|
+ */
|
|
|
static inline void skb_postpush_rcsum(struct sk_buff *skb,
|
|
|
const void *start, unsigned int len)
|
|
|
{
|
|
|
- /* For performing the reverse operation to skb_postpull_rcsum(),
|
|
|
- * we can instead of ...
|
|
|
- *
|
|
|
- * skb->csum = csum_add(skb->csum, csum_partial(start, len, 0));
|
|
|
- *
|
|
|
- * ... just use this equivalent version here to save a few
|
|
|
- * instructions. Feeding csum of 0 in csum_partial() and later
|
|
|
- * on adding skb->csum is equivalent to feed skb->csum in the
|
|
|
- * first place.
|
|
|
- */
|
|
|
- if (skb->ip_summed == CHECKSUM_COMPLETE)
|
|
|
- skb->csum = csum_partial(start, len, skb->csum);
|
|
|
+ __skb_postpush_rcsum(skb, start, len, 0);
|
|
|
}
|
|
|
|
|
|
+unsigned char *skb_pull_rcsum(struct sk_buff *skb, unsigned int len);
|
|
|
+
|
|
|
/**
|
|
|
* skb_push_rcsum - push skb and update receive checksum
|
|
|
* @skb: buffer to update
|