mems_internals.c
来自「disksim是一个非常优秀的磁盘仿真工具」· C语言 代码 · 共 1,010 行 · 第 1/2 页
C
1,010 行
* * begin = current velocity; end = new velocity; * below = new position BELOW current position; * above = new position ABOVE current position * * begin UP end UP below (1) turn, seek, turn * above (2) seek * * end DOWN below (3) turn, seek * above (4) seek, turn * * begin DOWN end UP below (5) seek, turn * above (6) turn, seek * * end DOWN below (7) seek * above (8) turn, seek, turn */ /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: begin->y_vel = %d, end->y_vel = %d\n", begin->y_vel, end->y_vel); fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: begin->y_pos = %d, end->y1_pos = %d\n", begin->y_pos, end->y1_pos); fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: end->y1_pos = %d, end->y2_pos = %d\n", end->y1_pos, end->y2_pos); */ turnaround_time = 0.0; number_of_turns = 0; if (begin->y_vel >= 0) { if (end->y_vel > 0) { /* final direction == begining direction */ if (begin->y_pos >= end->y_pos) { /* case (1) */ turnaround_time = find_turnaround_time((begin->y_pos * bit_width), begin->y_vel, y_accel, spring_factor, y_length_nm); turnaround_time += find_turnaround_time((end->y_pos * bit_width), end->y_vel, y_accel, spring_factor, y_length_nm); number_of_turns = 2; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 1 - turnaround_time = %f\n", turnaround_time); */ } else { /* no need to turn around */ /* case (2) */ number_of_turns = 0; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 2 - turnaround_time = %f\n", turnaround_time); */ } } else { /* final direction != begining direction */ if (begin->y_pos >= end->y_pos) { /* case (3) */ turnaround_time = find_turnaround_time((begin->y_pos * bit_width), begin->y_vel, y_accel, spring_factor, y_length_nm); number_of_turns = 1; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 3 - turnaround_time = %f\n", turnaround_time); */ } else { /* case (4) */ turnaround_time = find_turnaround_time((end->y_pos * bit_width), end->y_vel, y_accel, spring_factor, y_length_nm); number_of_turns = 1; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 4 - turnaround_time = %f\n", turnaround_time); */ } } } else { /* begin.y_vel < 0.0 */ if (end->y_vel > 0) { /* final direction != begining direction */ if (begin->y_pos >= end->y_pos) { /* case (5) */ turnaround_time = find_turnaround_time((end->y_pos * bit_width), end->y_vel, y_accel, spring_factor, y_length_nm); number_of_turns = 1; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 5 - turnaround_time = %f\n", turnaround_time); */ } else { /* case (6) */ turnaround_time = find_turnaround_time((begin->y_pos * bit_width), begin->y_vel, y_accel, spring_factor, y_length_nm); number_of_turns = 1; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 6 - turnaround_time = %f\n", turnaround_time); */ } } else { /* final direction == begining direction */ if (begin->y_pos >= end->y_pos) { /* no need to turn around */ /* case (7) */ number_of_turns = 0; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 7 - turnaround_time = %f\n", turnaround_time); */ dist_y_equiv_nm = 0; } else { /* case (8) */ turnaround_time = find_turnaround_time((begin->y_pos * bit_width), begin->y_vel, y_accel, spring_factor, y_length_nm); turnaround_time += find_turnaround_time((end->y_pos * bit_width), end->y_vel, y_accel, spring_factor, y_length_nm); number_of_turns = 2; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: finding turnarounds - case 8 - turnaround_time = %f\n", turnaround_time); */ } } } dist_y_nm = (double)abs(end->y_pos - begin->y_pos) * sled->bit_length_nm; /* fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: begin->y_pos = %d, bit_width = %f, y_begin_nm = %f\n", begin->y_pos, bit_width, y_begin_nm); fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: end->y1_pos = %d, bit_width = %f, y_end_nm = %f\n", end->y1_pos, bit_width, y_end_nm); fprintf(__OUTPUTFILE__, "memsdevice_seek_time:: find_seek_time_piecewise - y_begin_nm = %f, y_end_nm = %f\n", y_begin_nm, y_end_nm); */ if (sled->dev->seek_function == MEMS_SEEK_HONG) { seek_time_y = find_seek_time_hong_y((begin->y_pos * bit_width), (end->y_pos * bit_width), spring_factor, y_accel, y_length_nm, y_access_speed_nm_s) + turnaround_time; } else { if (sled->dev->precompute_seek_count > 0) { seek_time_y = mems_find_precomputed_seek_time(sled, (begin->y_pos * bit_width), (end->y_pos * bit_width), _Y_SEEK_) + turnaround_time; } else { seek_time_y = find_seek_time_piecewise((begin->y_pos * bit_width), (end->y_pos * bit_width), spring_factor, y_accel, y_length_nm, y_access_speed_nm_s) + turnaround_time; } } /* if (distance != NULL) { if (distance_direction == 1) { *distance = (int)sqrt(dist_x_nm * dist_x_nm + ((dist_y_nm + dist_y_equiv_nm) * (dist_y_nm + dist_y_equiv_nm))); } else { *distance = (int)sqrt(dist_x_nm * dist_x_nm + dist_y_nm * dist_y_nm); } // fprintf (__OUTPUTFILE__, "dist_x = %f, dist_y = %f; dist = %d\n", dist_x_nm, dist_y_nm, *distance); } */ if (return_turnaround_time != NULL) { *return_turnaround_time = (turnaround_time) * 1000.0; } if (return_turnaround_number != NULL) { *return_turnaround_number = number_of_turns; } if (return_x_seek_time != NULL) { *return_x_seek_time = seek_time_x * 1000.0; } if (return_y_seek_time != NULL) { *return_y_seek_time = seek_time_y * 1000.0; } /* fprintf (stderr, "turnaround_time = %f, number_of_turns = %d\n", (turnaround_time * 1000.0), number_of_turns); */ if (_VERBOSE_) { printf("dist_x = %f; dist_y = %f; seek_time_x = %f; seek_time_y = %f\n", dist_x_nm, dist_y_nm, seek_time_x, seek_time_y); } /* total seek time is the max of the seek time in the two dimensions */ total_time = max(seek_time_x, seek_time_y); /* convert to milliseconds */ return (total_time * (double)1000.0);}/*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- * This implements the seek cache. *-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/doublemems_seek_time_seekcache (mems_sled_t *sled, coord_t *begin, coord_t *end, double *return_x_seek_time, double *return_y_seek_time, double *return_turnaround_time, int *return_turnaround_number){ struct mems_seekcache *s; int i; /* First check if value is cached */ for (i = 0; i < MEMS_SEEKCACHE; i++) { s = &sled->seekcache[i]; if (mems_equal_coords(begin, &s->begin) && mems_equal_coords(end, &s->end)) { if (return_x_seek_time) *return_x_seek_time = s->x_seek_time; if (return_y_seek_time) *return_y_seek_time = s->y_seek_time; if (return_turnaround_time) *return_turnaround_time = s->turnaround_time; if (return_turnaround_number) *return_turnaround_number = s->turnaround_number; return s->time; } } s = &sled->seekcache[sled->seekcache_next]; mems_coord_t_copy(begin, &s->begin); mems_coord_t_copy(end, &s->end); s->time = mems_seek_time(sled, &s->begin, &s->end, &s->x_seek_time, &s->y_seek_time, &s->turnaround_time, &s->turnaround_number); if (return_x_seek_time) *return_x_seek_time = s->x_seek_time; if (return_y_seek_time) *return_y_seek_time = s->y_seek_time; if (return_turnaround_time) *return_turnaround_time = s->turnaround_time; if (return_turnaround_number) *return_turnaround_number = s->turnaround_number; sled->seekcache_next++; if (sled->seekcache_next == MEMS_SEEKCACHE) sled->seekcache_next = 0; // fprintf(stderr, "mems_seek_time_seekcache:: s->time = %f\n", s->time); return s->time;}/*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- * These implement the pre-computed seek functions *-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/voidmems_print_precomputed_seek_times(mems_t *dev) { int i; for (i = 0; i <= dev->precompute_seek_count; i++) { printf("i = %d, distance = %d, x_seek = %f, y_seek = %f\n", i, dev->precompute_seek_distances[i], dev->precompute_x_seek_times[i], dev->precompute_y_seek_times[i]); }}doublemems_find_precomputed_seek_time(mems_sled_t *sled, double start_offset_nm, double end_offset_nm, int direction) { double seektime = 0.0; int dist_nm; int i; mems_t *dev = sled->dev; dist_nm = (int)find_dist_nm(start_offset_nm, end_offset_nm); if (_VERBOSE_) { fprintf(__OUTPUTFILE__, "mems_find_precomputed_seek_time:: entry - start_offset_nm = %f, end_offset_nm = %f\n", start_offset_nm, end_offset_nm); fprintf(__OUTPUTFILE__, "mems_find_precomputed_seek_time:: dist_nm = %d\n", dist_nm); } // fprintf(stderr, "dist_nm = %d\n", dist_nm); // mems_print_precomputed_seek_times(dev); if (dist_nm) { for (i=0; i <= dev->precompute_seek_count; i++) { /* printf("i = %d, dist = %d, x_seek = %f, y_seek = %f\n", i, dev->precompute_seek_distances[i], dev->precompute_x_seek_times[i], dev->precompute_y_seek_times[i]); */ if (dist_nm <= dev->precompute_seek_distances[i]) { if (dist_nm == dev->precompute_seek_distances[i]) { // fprintf(stderr, "found precomputed seek distance %d\n", dist_nm); seektime = (direction == _X_SEEK_) ? dev->precompute_x_seek_times[i] : dev->precompute_y_seek_times[i]; } else { double ddiff = (double) (dist_nm - dev->precompute_seek_distances[(i-1)]) / (double) (dev->precompute_seek_distances[i] - dev->precompute_seek_distances[(i-1)]); /* fprintf(stderr, "did not find precompute seek distance %d\n", dist_nm); fprintf(stderr, "ddiff = %f\n", ddiff); fprintf(stderr, "i = %d\n", i); */ if (direction == _X_SEEK_) { seektime = dev->precompute_x_seek_times[(i-1)]; // fprintf(stderr, "seektime = %f\n", seektime); seektime += ddiff * (dev->precompute_x_seek_times[i] - dev->precompute_x_seek_times[(i-1)]); /* fprintf(stderr, "times[i] = %f, times[i-1] = %f\n", dev->precompute_x_seek_times[i], dev->precompute_x_seek_times[(i-1)]); fprintf(stderr, "seektime = %f\n", seektime); */ } else { seektime = dev->precompute_y_seek_times[(i-1)]; // fprintf(stderr, "seektime = %f\n", seektime); seektime += ddiff * (dev->precompute_y_seek_times[i] - dev->precompute_y_seek_times[(i-1)]); /* fprintf(stderr, "times[i] = %f, times[i-1] = %f\n", dev->precompute_y_seek_times[i], dev->precompute_y_seek_times[(i-1)]); fprintf(stderr, "seektime = %f\n", seektime); */ } } break; } } if (seektime == 0.0) { fprintf(stderr, "Seek distance exceeds precompute seek curve: %d\n", dist_nm); exit(0); } } if (_VERBOSE_) { fprintf(__OUTPUTFILE__, "mems_find_precompute_seek_time:: finished - seektime = %f\n", seektime); } // fprintf(stderr, "seektime / 1000.0 = %f\n", (seektime / 1000.0)); return(seektime / 1000.0);}voidmems_precompute_seek_curve(mems_t *dev) { coord_t begin, end; double x_seek_time, y_seek_time; int sled_length_bits; int offset; int bit_step; int nm_step; int i; double num_time_constants = dev->sled[0].num_time_constants; int precompute_seek_count = dev->precompute_seek_count; dev->sled[0].num_time_constants = 0.0; dev->precompute_seek_count = 0; sled_length_bits = (int) (dev->sled[0].x_length_nm / dev->sled[0].bit_length_nm); bit_step = sled_length_bits / precompute_seek_count; nm_step = (sled_length_bits * dev->sled[0].bit_length_nm) / precompute_seek_count; dev->precompute_seek_distances = (int *)malloc((precompute_seek_count + 1) * sizeof(int)); dev->precompute_x_seek_times = (double *)malloc((precompute_seek_count + 1) * sizeof(double)); dev->precompute_y_seek_times = (double *)malloc((precompute_seek_count + 1) * sizeof(double)); /* printf("precompute_seek_count = %d, bit_step = %d, nm_step = %d\n", precompute_seek_count, bit_step, nm_step); */ // for(offset = 0; offset <= sled_length_bits; offset += bit_step) { for(i = 0; i < precompute_seek_count; i++) { offset = i * bit_step; // if (verbose) fprintf(stdout, "main: starting a new seek (monkey)\n"); begin.x_pos = 0; begin.y_pos = 0; begin.y_vel = 0; end.x_pos = offset; end.y_pos = 0; end.y_vel = 0; /* printf("begin = %d, end = %d\n", begin.y_vel, end.y_vel); */ x_seek_time = mems_seek_time(&(dev->sled[0]), &begin, &end, NULL, NULL, NULL, NULL); begin.x_pos = 0; begin.y_pos = 0; begin.y_vel = dev->sled[0].y_access_speed_bit_s; end.x_pos = 0; end.y_pos = offset; end.y_vel = dev->sled[0].y_access_speed_bit_s; /* printf("begin = %d, end = %d\n", begin.y_pos, end.y_pos); */ y_seek_time = mems_seek_time(&(dev->sled[0]), &begin, &end, NULL, NULL, NULL, NULL); /* fprintf(stdout, "%d, %d, %d, %f, %f\n", i, (i * nm_step), (offset * dev->sled[0].bit_length_nm), x_seek_time, y_seek_time); */ dev->precompute_seek_distances[i] = offset * dev->sled[0].bit_length_nm; dev->precompute_x_seek_times[i] = x_seek_time; dev->precompute_y_seek_times[i] = y_seek_time; /* fprintf(stdout, "%d, %d, %f, %f\n", i, (offset * dev->sled[0].bit_length_nm), dev->precompute_x_seek_times[i], dev->precompute_y_seek_times[i]); */ } begin.x_pos = 0; begin.y_pos = 0; begin.y_vel = 0; end.x_pos = sled_length_bits; end.y_pos = 0; end.y_vel = 0; x_seek_time = mems_seek_time(&(dev->sled[0]), &begin, &end, NULL, NULL, NULL, NULL); begin.x_pos = 0; begin.y_pos = 0; begin.y_vel = dev->sled[0].y_access_speed_bit_s; end.x_pos = 0; end.y_pos = sled_length_bits; end.y_vel = dev->sled[0].y_access_speed_bit_s; y_seek_time = mems_seek_time(&(dev->sled[0]), &begin, &end, NULL, NULL, NULL, NULL); dev->precompute_seek_distances[precompute_seek_count] = sled_length_bits * dev->sled[0].bit_length_nm; dev->precompute_x_seek_times[precompute_seek_count] = x_seek_time; dev->precompute_y_seek_times[precompute_seek_count] = y_seek_time; /* fprintf(stdout, "%d, %d, %d, %f, %f\n", precompute_seek_count, (precompute_seek_count * nm_step), sled_length_bits * dev->sled[0].bit_length_nm, x_seek_time, y_seek_time); */ dev->sled[0].num_time_constants = num_time_constants; dev->precompute_seek_count = precompute_seek_count;}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?