+ time_t how_much_seconds = time(NULL) - get_mtime(classmap); /* sice start of daily aggregation session */\r
+ printf("Reading %s (%ld seconds old) and applying Fair Use Policy and Aggregation rules... \n", classmap, how_much_seconds);\r
+ \r
+ parse(classmap)\r
+ {\r
+ ptr=strchr(_,' ');\r
+ if(ptr)\r
+ {\r
+ *ptr=0;\r
+ ptr++;\r
+ if_exists(ip,ips,eq(ip->addr,_))\r
+ {\r
+ int unshape_this_ip = 0;\r
+ long avg_mbps_down = ip->traffic_down * 8 / how_much_seconds; \r
+ long avg_mbps_up = ip->traffic_up * 8 / how_much_seconds;\r
+ int agreg = 1, print_stats = 1;\r
+ \r
+ if(ip->keyword->download_aggregation)\r
+ {\r
+ int min_mbps = (ip->min/ip->keyword->download_aggregation)>>10;\r
+ if(min_mbps < 1)\r
+ {\r
+ min_mbps = 1;\r
+ }\r
+ \r
+ if(min_mbps <= avg_mbps_down)\r
+ {\r
+ unshape_this_ip = 0;\r
+ agreg = (int)((float)(avg_mbps_down+1)/min_mbps+.5);\r
+ ip->max /= agreg;\r
+ ip->pps_limit /= agreg;\r
+ printf("Download aggregation 1:%d for %s (min: %d Mbps avg: %ld Mbps)\n", agreg, ip->name, min_mbps, avg_mbps_down);\r
+ }\r
+ else\r
+ {\r
+ unshape_this_ip = 1;\r
+ }\r
+ }\r
+ else if(ip->keyword->upload_aggregation)\r
+ {\r
+ int min_mbps = (ip->min/ip->keyword->upload_aggregation)>>10;\r
+ if(min_mbps < 1)\r
+ {\r
+ min_mbps = 1;\r
+ }\r
+\r
+ if(min_mbps <= avg_mbps_up)\r
+ {\r
+ unshape_this_ip = 0;\r
+ agreg = (int)((float)(avg_mbps_up+1)/min_mbps+.5);\r
+ ip->max /= agreg;\r
+ printf("Upload aggregation 1:%d for %s: (min: %d Mbps avg: %ld Mbps)\n", agreg, ip->name, min_mbps, avg_mbps_up);\r
+ }\r
+ else\r
+ {\r
+ unshape_this_ip = 1;\r
+ }\r
+ }\r
+ if(stop_shaping)\r
+ {\r
+ unshape_this_ip = 1;\r
+ }\r
+ ip->aggregated = agreg; \r
+ ip->mark = atoi(ptr);\r
+ if(ip->max < ip->desired || unshape_this_ip || reduce_ceil) /* apply or disable FUP limit immediately.... */\r
+ {\r
+ if(unshape_this_ip)\r
+ {\r
+ ip->max = ip->desired;\r
+ if(stop_shaping) /* all limits removed, but not printed with -s (start_shaping) switch */\r
+ {\r
+ printf("Removing limit for %s (%s) ", ip->name, ip->addr);\r
+ }\r
+ else\r
+ {\r
+ print_stats = 0;\r
+ }\r
+ }\r
+ else\r
+ {\r
+ printf("Updating %s (%s) ", ip->name, ip->addr);\r
+ if(reduce_ceil)\r
+ {\r
+ ip->max = ip->min + (ip->desired-ip->min)/reduce_ceil;\r
+ }\r
+ else if(ip->max < ip->min)\r
+ {\r
+ ip->max = ip->min;\r
+ } \r
+ }\r
+ for_each(interface, interfaces)\r
+ {\r
+ if(!interface->is_upstream)\r
+ {\r
+ if(print_stats)\r
+ {\r
+ printf("[down %s: %dk-%dk wants %d]", interface->name, ip->min, ip->max, ip->desired);\r
+ }\r
+ sprintf(str, "%s class change dev %s parent 1:%d classid 1:%d htb rate %dkbit ceil %dkbit burst %dk prio %d quantum %d", \r
+ tc, interface->name, ip->group, ip->mark, ip->min, ip->max, burst, ip->prio, htb_quantum);\r
+ safe_run(str);\r
+ }\r
+ else\r
+ {\r
+ if(print_stats)\r
+ {\r
+ printf("[up %s: %dk-%dk wants %dk]", interface->name, (int)((ip->min/ip->keyword->asymetry_ratio)-ip->keyword->asymetry_fixed), \r
+ (int)((ip->desired/ip->keyword->asymetry_ratio)-ip->keyword->asymetry_fixed),\r
+ (int)((ip->desired/ip->keyword->asymetry_ratio)-ip->keyword->asymetry_fixed));\r
+ }\r
+ sprintf(str,"%s class change dev %s parent 1:%d classid 1:%d htb rate %dkbit ceil %dkbit burst %dk prio %d quantum %d",\r
+ tc, interface->name, ip->group, ip->mark,\r
+ (int)((ip->min/ip->keyword->asymetry_ratio)-ip->keyword->asymetry_fixed),\r
+ (int)((ip->max/ip->keyword->asymetry_ratio)-ip->keyword->asymetry_fixed), burst, ip->prio, htb_quantum);\r
+ safe_run(str);\r
+ }\r
+ }\r
+ if(print_stats)\r
+ {\r
+ printf("\n");\r
+ }\r
+ }\r
+ }\r
+ }\r
+ }\r
+ fail\r
+ { \r
+ perror(classmap);\r
+ puts("Warning - classmap file not fund, just generating preview ...");\r
+ start_shaping=FALSE;\r
+ stop_shaping=FALSE;\r
+ }\r
+ done; /* ugly macro end */\r