132}
133
134
135
136
137
138
139
140
141int tfrc_lh_interval_add(struct tfrc_loss_hist *lh, struct tfrc_rx_hist *rh,
142 u32 (*calc_first_li)(struct sock *), struct sock *sk)
143{
144 struct tfrc_loss_interval *cur = tfrc_lh_peek(lh), *new;
145
146 if (cur != NULL && !tfrc_lh_is_new_loss(cur, tfrc_rx_hist_loss_prev(rh)))
147 return 0;
148
149 new = tfrc_lh_demand_next(lh);
150 if (unlikely(new == NULL)) {
151 DCCP_CRIT("Cannot allocate/add loss record.");
152 return 0;
153 }
154
155 new->li_seqno = tfrc_rx_hist_loss_prev(rh)->tfrchrx_seqno;
156 new->li_ccval = tfrc_rx_hist_loss_prev(rh)->tfrchrx_ccval;
157 new->li_is_closed = 0;
158
159 if (++lh->counter == 1)
160 lh->i_mean = new->li_length = (*calc_first_li)(sk);
161 else {
162 cur->li_length = dccp_delta_seqno(cur->li_seqno, new->li_seqno);
163 new->li_length = dccp_delta_seqno(new->li_seqno,
164 tfrc_rx_hist_last_rcv(rh)->tfrchrx_seqno) + 1;
165 if (lh->counter > (2*LIH_SIZE))
166 lh->counter -= LIH_SIZE;
167
168 tfrc_lh_calc_i_mean(lh);
169 }
170 return 1;
171}
172EXPORT_SYMBOL_GPL(tfrc_lh_interval_add);