#include <fwp.h>
#include "fwp_idl.h"
#include "fwp_admctrl.h"
+#include <ul_log.h>
+#include <ul_logreg.h>
+#include "fwp_utils.h"
+
+UL_LOG_CUST(ulogd_fwp_admctrl);
+ul_log_domain_t ulogd_fwp_admctrl = {UL_LOGL_MSG, "fwp_admctrl"};
+UL_LOGREG_SINGLE_DOMAIN_INIT_FUNCTION(fwp_admctrl_logreg_domains, ulogd_fwp_admctrl);
/* TODO: Find out the real value and determine what influences it (MTU
* of the interface minus header sizes?). */
bool *schedulable)
{
int utilization = 0;
-
- const int rate = 54*1000*1000;
- const bool erp_ofdm = true;
- const bool short_preamble = true;
- struct fres_sa_contract *c, *c_new = NULL;
+ struct frm_fwp_priv *pr = priv;
+ const int rate = pr->rate_mbps*1000*1000;
+ struct fres_sa_contract *c;
long int period_usec;
- fres_block_basic *basic;
fres_block_fwp_sched *fwp_sched;
size_t bytes;
basic = fres_contract_get_basic(c->contract);
frsh_network_budget_to_bytes(FRSH_NETPF_FWP,&basic->budget,&bytes);
- printf(" processing: id=%s, period=%ld ms, budget=%lu bytes\n",
+ ul_logmsg("processing: id=%s, period=%ld ms, budget=%lu bytes\n",
id,
fosa_rel_time_to_msec(basic->period),
(long unsigned int)bytes);
+ period_usec = basic ? fosa_rel_time_to_msec(basic->period)*1000 : 0;
+
/* Calculate protocol overhead */
fragments = (bytes + MTU - 1) / MTU;
- if (fragments == 0)
+ if (fragments == 0 && period_usec != 0)
continue;
const int data_overhead = UDP_HEADER_SIZE + IP_HEADER_SIZE +
LLC_HEADER_SIZE + MAC_FCS_SIZE;
duration_usec = frame_duration(data_overhead + bytes%MTU, rate,
- erp_ofdm, short_preamble);
- tmp_usec = frame_duration(data_overhead + MTU, rate, erp_ofdm,
- short_preamble);
+ pr->erp_ofdm, pr->short_preamble);
+ tmp_usec = frame_duration(data_overhead + MTU, rate,
+ pr->erp_ofdm, pr->short_preamble);
duration_usec += tmp_usec*(fragments-1);
/* Add average backoff - assume there is no collision */
tmp_usec = ASLOTTIME_USEC*fragments*pisvejc[ac];
duration_usec += (aifsn[ac] + cwmin[ac]/2)*tmp_usec;
/* We use ACK and ignore burst */
- tmp_usec = frame_duration(ACK_FRAME_SIZE, rate, erp_ofdm,
- short_preamble) + ASIFSTIME_USEC;
+ tmp_usec = frame_duration(ACK_FRAME_SIZE, rate,
+ pr->erp_ofdm, pr->short_preamble)
+ + ASIFSTIME_USEC;
duration_usec += fragments * tmp_usec;
//printf("duration: %ld ms\n", duration_usec/1000);
/* TODO: If STA-to-STA, multiply it by two. Note that
* AP may use different values for backoff. */
- //duration_usec *= 2; /* For demo, we have always STA-to-STA */
+ duration_usec *= 2; /* For demo, we have always STA-to-STA */
- basic = fres_contract_get_basic(c->contract);
- period_usec = fosa_rel_time_to_msec(basic->period)*1000;
if (c->contract == c->new) {
- c_new = c;
if (period_usec == 0) {
+ ul_logmsg("Period is zero!\n");
goto not_schedulable;
}
+
+ frsh_rel_time_t deadline;
+ long int d;
+ if (fres_contract_get_deadline(&c->contract, &deadline)) {
+ d = fosa_rel_time_to_msec(deadline)*1000;
+ } else {
+ d = 100/*sec*/*1000*1000;
+ }
+ if (d < 30/*msec*/*1000) {
+ ul_logmsg("Deadline shorter than 30 ms!\n");
+ goto not_schedulable;
+ };
+
+ fwp_sched = malloc(sizeof(*fwp_sched));
+ fwp_sched->ac_id =
+ d < 100*1000 ? FWP_AC_VO :
+ d < 500*1000 ? FWP_AC_VI :
+ d < 1000*1000 ? FWP_AC_BE :
+ FWP_AC_BK;
+ fres_contract_add_block(c->contract, FRES_BLOCK_FWP_SCHED, fwp_sched);
}
+
utilization += (long long)(duration_usec * 10000) / period_usec;
}
- if (!c_new) {
- *schedulable = false;
- return -1;
- }
- if (utilization >= 10000 * 96/100) {
+ if (utilization >= 10000 * 96/100 && !pr->bypass) {
goto not_schedulable;
}
scenario->utilization = utilization/100; /* For GUI */
-
- basic = fres_contract_get_basic(c_new->contract);
- /*int d = c->deadline_usec;*/
- long int d = fosa_rel_time_to_msec(basic->period)*1000;
- if (d <= 0) d = 100*1000*1000;
- if (d < 30000) {
- goto not_schedulable;
- };
-
+
+ ul_logmsg("accepted (utilization=%d%%)\n", utilization/100);
*schedulable = true;
- fwp_sched = malloc(sizeof(*fwp_sched));
- fwp_sched->ac_id =
- d < 100*1000 ? FWP_AC_VO :
- d < 500*1000 ? FWP_AC_VI :
- d < 1000*1000 ? FWP_AC_BE :
- FWP_AC_BK;
- fres_contract_add_block(c_new->contract, FRES_BLOCK_FWP_SCHED, fwp_sched);
return 0;
not_schedulable:
+ ul_logmsg("rejected (utilization=%d%%)\n", utilization/100);
*schedulable = false;
return 0;
}