/* Expands 'hmap', if necessary, to optimize the performance of searches when * it has up to 'n' elements. (But iteration will be slow in a hash map whose * allocated capacity is much higher than its current number of nodes.) */ void hmap_reserve(struct hmap *hmap, size_t n) { size_t new_mask = calc_mask(n); if (new_mask > hmap->mask) { resize(hmap, new_mask); } }
/* Shrinks 'hmap', if necessary, to optimize the performance of iteration. */ void hmap_shrink(struct hmap *hmap) { size_t new_mask = calc_mask(hmap->n); if (new_mask < hmap->mask) { resize(hmap, new_mask); } }
/* Expands 'hmap', if necessary, to optimize the performance of searches. */ void hmap_expand(struct hmap *hmap) { size_t new_mask = calc_mask(hmap->n); if (new_mask > hmap->mask) { resize(hmap, new_mask); } }
/* Expands 'hmap', if necessary, to optimize the performance of searches when * it has up to 'n' elements. (But iteration will be slow in a hash map whose * allocated capacity is much higher than its current number of nodes.) * * ('where' is used in debug logging. Commonly one would use hmap_reserve() to * automatically provide the caller's source file and line number for * 'where'.) */ void hmap_reserve_at(struct hmap *hmap, size_t n, const char *where) { size_t new_mask = calc_mask(n); if (new_mask > hmap->mask) { COVERAGE_INC(hmap_reserve); resize(hmap, new_mask, where); } }
/* Shrinks 'hmap', if necessary, to optimize the performance of iteration. * * ('where' is used in debug logging. Commonly one would use hmap_shrink() to * automatically provide the caller's source file and line number for * 'where'.) */ void hmap_shrink_at(struct hmap *hmap, const char *where) { size_t new_mask = calc_mask(hmap->n); if (new_mask < hmap->mask) { COVERAGE_INC(hmap_shrink); resize(hmap, new_mask, where); } }
int main(int argc, char **argv) { fd_set rdfs; int s, t; struct sockaddr_can addr; struct can_filter rfilter; struct can_frame frame; int testcase = 0; int nbytes, ret; struct ifreq ifr; int ifindex; if ((s = socket(PF_CAN, SOCK_RAW, CAN_RAW)) < 0) { perror("socket"); return 1; } if ((t = socket(PF_CAN, SOCK_RAW, CAN_RAW)) < 0) { perror("socket"); return 1; } strcpy(ifr.ifr_name, "vcan0"); ioctl(s, SIOCGIFINDEX, &ifr); ifindex = ifr.ifr_ifindex; addr.can_family = AF_CAN; addr.can_ifindex = ifindex; if (bind(s, (struct sockaddr *)&addr, sizeof(addr)) < 0) { perror("bind"); return 1; } if (bind(t, (struct sockaddr *)&addr, sizeof(addr)) < 0) { perror("bind"); return 1; } rfilter.can_id = 0xF; /* receive only the filter requests */ rfilter.can_mask = CAN_SFF_MASK | CAN_EFF_FLAG | CAN_RTR_FLAG; setsockopt(s, SOL_CAN_RAW, CAN_RAW_FILTER, &rfilter, sizeof(rfilter)); /* disable default receive filter on the test socket */ setsockopt(t, SOL_CAN_RAW, CAN_RAW_FILTER, NULL, 0); while (1) { FD_ZERO(&rdfs); FD_SET(s, &rdfs); FD_SET(t, &rdfs); if ((ret = select(t+1, &rdfs, NULL, NULL, NULL)) < 0) { perror("select"); break; } if (FD_ISSET(s, &rdfs)) { if ((nbytes = read(s, &frame, sizeof(struct can_frame))) < 0) { perror("read"); exit(1); } if (nbytes < sizeof(struct can_frame)) { fprintf(stderr, "read: incomplete CAN frame\n"); exit(1); } if ((frame.can_id != 0xF) || (frame.can_dlc != 1)) { fprintf(stderr, "\nWrong request from master!\n"); exit(1); } testcase = frame.data[0]; if (testcase < 18) { rfilter.can_id = calc_id(testcase); rfilter.can_mask = calc_mask(testcase); setsockopt(t, SOL_CAN_RAW, CAN_RAW_FILTER, &rfilter, sizeof(rfilter)); printf("testcase %2d : can_id = 0x%08X can_mask = 0x%08X\n", testcase, rfilter.can_id, rfilter.can_mask); } frame.can_id = 0xFA; /* filter ack */ if (write(s, &frame, sizeof(frame)) < 0) { perror("write"); exit(1); } if (testcase > 17) break; } if (FD_ISSET(t, &rdfs)) { if ((nbytes = read(t, &frame, sizeof(struct can_frame))) < 0) { perror("read"); exit(1); } if (nbytes < sizeof(struct can_frame)) { fprintf(stderr, "read: incomplete CAN frame\n"); exit(1); } printf ("%08X\n", frame.can_id); } } printf("testcase %2d : Filtertest done.\n", testcase); close(s); close(t); return 0; }