/* * void * rmc_queue_packet(struct rm_class *cl, struct mbuf *m) - Add packet given by * mbuf 'm' to queue for resource class 'cl'. This routine is called * by a driver's if_output routine. This routine must be called with * output packet completion interrupts locked out (to avoid racing with * rmc_dequeue_next). * * Returns: 0 on successful queueing * -1 when packet drop occurs */ int rmc_queue_packet(struct rm_class *cl, struct mbuf *m) { struct timeval now; struct rm_ifdat *ifd = cl->ifdat_; int cpri = cl->pri_; int is_empty = qempty(cl->q_); RM_GETTIME(now); if (ifd->cutoff_ > 0) { if (TV_LT(&cl->undertime_, &now)) { if (ifd->cutoff_ > cl->depth_) ifd->cutoff_ = cl->depth_; CBQTRACE(rmc_queue_packet, 'ffoc', cl->depth_); } #if 1 /* ALTQ */ else { /* * the class is overlimit. if the class has * underlimit ancestors, set cutoff to the lowest * depth among them. */ struct rm_class *borrow = cl->borrow_; while (borrow != NULL && borrow->depth_ < ifd->cutoff_) { if (TV_LT(&borrow->undertime_, &now)) { ifd->cutoff_ = borrow->depth_; CBQTRACE(rmc_queue_packet, 'ffob', ifd->cutoff_); break; } borrow = borrow->borrow_; } } #else /* !ALTQ */ else if ((ifd->cutoff_ > 1) && cl->borrow_) { if (TV_LT(&cl->borrow_->undertime_, &now)) { ifd->cutoff_ = cl->borrow_->depth_; CBQTRACE(rmc_queue_packet, 'ffob', cl->borrow_->depth_); } } #endif /* !ALTQ */ }
/* * collect delay statistics on the upcalls */ static void collate(struct timeval *t) { u_long d; struct timeval tp; u_long delta; GET_TIME(tp); if (TV_LT(*t, tp)) { TV_DELTA(tp, *t, delta); d = delta >> 10; if (d > UPCALL_MAX) d = UPCALL_MAX; ++upcall_data[d]; }
int nanosleep ( const struct timespec *rqtp, /* time to delay */ struct timespec *rmtp /* premature wakeup (NULL=no result) */ ) { int status; /* int oldErrno; */ ULONG delayTicks; struct timespec then; struct timespec now; int returnStatus; int savtype; if (rqtp == NULL || !TV_VALID(*rqtp)) { errno = EINVAL; return (ERROR); } if (TV_ISZERO(*rqtp)) return (OK); if (_func_pthread_setcanceltype != NULL) { _func_pthread_setcanceltype(PTHREAD_CANCEL_ASYNCHRONOUS, &savtype); } (void)clockLibInit (); /* make sure clock "running" */ (void)clock_gettime (CLOCK_REALTIME, &then); TV_CONVERT_TO_TICK (delayTicks, *rqtp); /* return's 1 (RESTART) if interrupted sleep */ status = taskDelay (delayTicks); if (status == 0) returnStatus = 0; else returnStatus = -1; if (rmtp != NULL) { (void)clock_gettime (CLOCK_REALTIME, &now); TV_SUB (now, then); /* make time relative to start */ if (TV_LT(now, *rqtp)) { TV_SET(*rmtp, *rqtp); TV_SUB(*rmtp, now); } else TV_ZERO((*rmtp)); } if (_func_pthread_setcanceltype != NULL) { _func_pthread_setcanceltype(savtype, NULL); } return (returnStatus); }
PRIVATE int time_compare(pq_obj p1, pq_obj p2) { return( TV_LT( TP( p1 )->t_expiration, TP( p2 )->t_expiration ) ) ; }
/** * Parse the time columns of a record in a CSV file and set the record time. * * If an error occurs in this function it will be appended to the log and * error mail messages, and the process status will be set appropriately. * * @param csv pointer to the CSVParser structure * @param record_index record index * * @retval 1 if successful * @retval 0 if invalid time format * @retval -1 if an error occurred */ int _csv_parse_record_time( CSVParser *csv, int record_index) { char *time_string; int status; int tci, fi; RETimeList *tc_patterns; RETimeRes match; RETimeRes result; int used_file_date; timeval_t rec_time; timeval_t prev_time; int tro_interval; double delta_t; struct tm gmt; /* Get the time column indexes */ if (!csv->tc_index) { if (!_csv_create_tc_index(csv)) { return(-1); } } /* Parse time strings and merge results */ for (tci = 0; tci < csv->ntc; ++tci) { fi = csv->tc_index[tci]; tc_patterns = csv->tc_patterns[tci]; /* Make sure this is a valid field index */ if (fi < 0 || fi > csv->nfields) { ERROR( DSPROC_LIB_NAME, "Time column index '%d' is out of range [0, %d].\n", fi, csv->nfields); dsproc_set_status(DSPROC_ECSVPARSER); return(-1); } time_string = csv->values[fi][record_index]; /* Parse time string */ status = retime_list_execute(tc_patterns, time_string, &match); if (status < 0) { ERROR( DSPROC_LIB_NAME, "Time string pattern match failed for record %d.\n", record_index + 1); dsproc_set_status(DSPROC_ECSVPARSER); return(-1); } else if (status == 0) { DSPROC_BAD_RECORD_WARNING(csv->file_name, csv->nrecs, "Record time format '%s' does not match '%s'\n", time_string, tc_patterns->retimes[tc_patterns->npatterns - 1]->tspattern); return(0); } /* Merge results */ if (tci == 0) { result = match; } else { if (match.year != -1) result.year = match.year; if (match.month != -1) result.month = match.month; if (match.mday != -1) result.mday = match.mday; if (match.hour != -1) result.hour = match.hour; if (match.min != -1) result.min = match.min; if (match.sec != -1) result.sec = match.sec; if (match.usec != -1) result.usec = match.usec; if (match.century != -1) result.century = match.century; if (match.yy != -1) result.yy = match.yy; if (match.yday != -1) result.yday = match.yday; if (match.secs1970 != -1) result.secs1970 = match.secs1970; } } if (result.secs1970 != -1) { csv->tvs[record_index].tv_sec = result.secs1970; csv->tvs[record_index].tv_usec = (result.usec == -1) ? 0 : result.usec; csv->tvs[record_index].tv_sec += csv->time_offset; csv->tvs[record_index].tv_sec += csv->tro_offset; return(1); } /* Check if we need to use the date from the file name */ used_file_date = 0; if (csv->ft_patterns) { if (!csv->ft_result) { csv->ft_result = calloc(1, sizeof(RETimeRes)); if (!csv->ft_result) { ERROR( DSPROC_LIB_NAME, "Memory allocation error creating file name RETimeRes structure\n"); dsproc_set_status(DSPROC_ECSVPARSER); return(-1); } status = dsproc_get_csv_file_name_time(csv, csv->file_name, csv->ft_result); if (status < 0) return(-1); } if (result.year == -1) { if (csv->ft_result->year != -1) { result.year = csv->ft_result->year; used_file_date = 1; } else { ERROR( DSPROC_LIB_NAME, "Could not determine record time\n" " -> year not found in record or file name time patterns\n"); dsproc_set_status(DSPROC_ECSVPARSER); return(-1); } } if (result.month == -1) { if (result.yday != -1) { yday_to_mday(result.yday, &(result.year), &(result.month), &(result.mday)); } else if (csv->ft_result->month != -1) { result.month = csv->ft_result->month; used_file_date = 2; } else if (csv->ft_result->yday != -1) { yday_to_mday(csv->ft_result->yday, &(result.year), &(result.month), &(result.mday)); used_file_date = 3; } } if (result.mday == -1) { if (csv->ft_result->mday != -1) { result.mday = csv->ft_result->mday; used_file_date = 3; } } } else { /* Verify that the year was found */ if (result.year == -1) { ERROR( DSPROC_LIB_NAME, "Could not determine record time\n" " -> year not found in record time pattern\n"); dsproc_set_status(DSPROC_ECSVPARSER); return(-1); } } rec_time = retime_get_timeval(&result); rec_time.tv_sec += csv->time_offset; rec_time.tv_sec += csv->tro_offset; /* Check for time rollovers if the file date was used */ if (used_file_date && record_index > 0) { prev_time = csv->tvs[record_index - 1]; if (TV_LT(rec_time, prev_time)) { switch (used_file_date) { case 1: /* yearly */ gmtime_r(&(prev_time.tv_sec), &gmt); if (IS_LEAP_YEAR(gmt.tm_year + 1900)) { tro_interval = 366 * 86400; } else { tro_interval = 365 * 86400; } if (!csv->tro_threshold) { csv->tro_threshold = 86400; } break; case 2: /* monthly */ gmtime_r(&(prev_time.tv_sec), &gmt); tro_interval = days_in_month(gmt.tm_year + 1900, gmt.tm_mon + 1) * 86400; if (!csv->tro_threshold) { csv->tro_threshold = 43200; } break; default: /* daily */ tro_interval = 86400; if (!csv->tro_threshold) { csv->tro_threshold = 3600; } } delta_t = (TV_DOUBLE(rec_time) + tro_interval) - TV_DOUBLE(prev_time); if ((delta_t > 0) && (delta_t < csv->tro_threshold)) { rec_time.tv_sec += tro_interval; csv->tro_offset += tro_interval; } } } if (record_index > 0) { prev_time = csv->tvs[record_index - 1]; } csv->tvs[record_index] = rec_time; return(1); }