diff options
Diffstat (limited to 'drivers/ide')
-rw-r--r-- | drivers/ide/ide-tape.c | 681 |
1 files changed, 271 insertions, 410 deletions
diff --git a/drivers/ide/ide-tape.c b/drivers/ide/ide-tape.c index bdf02fcc1a2..d8b02fb0284 100644 --- a/drivers/ide/ide-tape.c +++ b/drivers/ide/ide-tape.c @@ -75,37 +75,34 @@ enum { /* - * Pipelined mode parameters. + * Pipelined mode parameters. * - * We try to use the minimum number of stages which is enough to - * keep the tape constantly streaming. To accomplish that, we implement - * a feedback loop around the maximum number of stages: + * We try to use the minimum number of stages which is enough to keep the tape + * constantly streaming. To accomplish that, we implement a feedback loop around + * the maximum number of stages: * - * We start from MIN maximum stages (we will not even use MIN stages - * if we don't need them), increment it by RATE*(MAX-MIN) - * whenever we sense that the pipeline is empty, until we reach - * the optimum value or until we reach MAX. + * We start from MIN maximum stages (we will not even use MIN stages if we don't + * need them), increment it by RATE*(MAX-MIN) whenever we sense that the + * pipeline is empty, until we reach the optimum value or until we reach MAX. * - * Setting the following parameter to 0 is illegal: the pipelined mode - * cannot be disabled (idetape_calculate_speeds() divides by - * tape->max_stages.) + * Setting the following parameter to 0 is illegal: the pipelined mode cannot be + * disabled (idetape_calculate_speeds() divides by tape->max_stages.) */ #define IDETAPE_MIN_PIPELINE_STAGES 1 #define IDETAPE_MAX_PIPELINE_STAGES 400 #define IDETAPE_INCREASE_STAGES_RATE 20 /* - * After each failed packet command we issue a request sense command - * and retry the packet command IDETAPE_MAX_PC_RETRIES times. + * After each failed packet command we issue a request sense command and retry + * the packet command IDETAPE_MAX_PC_RETRIES times. * - * Setting IDETAPE_MAX_PC_RETRIES to 0 will disable retries. + * Setting IDETAPE_MAX_PC_RETRIES to 0 will disable retries. */ #define IDETAPE_MAX_PC_RETRIES 3 /* - * With each packet command, we allocate a buffer of - * IDETAPE_PC_BUFFER_SIZE bytes. This is used for several packet - * commands (Not for READ/WRITE commands). + * With each packet command, we allocate a buffer of IDETAPE_PC_BUFFER_SIZE + * bytes. This is used for several packet commands (Not for READ/WRITE commands) */ #define IDETAPE_PC_BUFFER_SIZE 256 @@ -124,48 +121,39 @@ enum { #define IDETAPE_WAIT_CMD (900*HZ) /* - * The following parameter is used to select the point in the internal - * tape fifo in which we will start to refill the buffer. Decreasing - * the following parameter will improve the system's latency and - * interactive response, while using a high value might improve system - * throughput. + * The following parameter is used to select the point in the internal tape fifo + * in which we will start to refill the buffer. Decreasing the following + * parameter will improve the system's latency and interactive response, while + * using a high value might improve system throughput. */ -#define IDETAPE_FIFO_THRESHOLD 2 +#define IDETAPE_FIFO_THRESHOLD 2 /* - * DSC polling parameters. + * DSC polling parameters. * - * Polling for DSC (a single bit in the status register) is a very - * important function in ide-tape. There are two cases in which we - * poll for DSC: + * Polling for DSC (a single bit in the status register) is a very important + * function in ide-tape. There are two cases in which we poll for DSC: * - * 1. Before a read/write packet command, to ensure that we - * can transfer data from/to the tape's data buffers, without - * causing an actual media access. In case the tape is not - * ready yet, we take out our request from the device - * request queue, so that ide.c will service requests from - * the other device on the same interface meanwhile. + * 1. Before a read/write packet command, to ensure that we can transfer data + * from/to the tape's data buffers, without causing an actual media access. + * In case the tape is not ready yet, we take out our request from the device + * request queue, so that ide.c could service requests from the other device + * on the same interface in the meantime. * - * 2. After the successful initialization of a "media access - * packet command", which is a command which can take a long - * time to complete (it can be several seconds or even an hour). + * 2. After the successful initialization of a "media access packet command", + * which is a command that can take a long time to complete (the interval can + * range from several seconds to even an hour). Again, we postpone our request + * in the middle to free the bus for the other device. The polling frequency + * here should be lower than the read/write frequency since those media access + * commands are slow. We start from a "fast" frequency - IDETAPE_DSC_MA_FAST + * (1 second), and if we don't receive DSC after IDETAPE_DSC_MA_THRESHOLD + * (5 min), we switch it to a lower frequency - IDETAPE_DSC_MA_SLOW (1 min). * - * Again, we postpone our request in the middle to free the bus - * for the other device. The polling frequency here should be - * lower than the read/write frequency since those media access - * commands are slow. We start from a "fast" frequency - - * IDETAPE_DSC_MA_FAST (one second), and if we don't receive DSC - * after IDETAPE_DSC_MA_THRESHOLD (5 minutes), we switch it to a - * lower frequency - IDETAPE_DSC_MA_SLOW (1 minute). - * - * We also set a timeout for the timer, in case something goes wrong. - * The timeout should be longer then the maximum execution time of a - * tape operation. - */ - -/* - * DSC timings. + * We also set a timeout for the timer, in case something goes wrong. The + * timeout should be longer then the maximum execution time of a tape operation. */ + +/* DSC timings. */ #define IDETAPE_DSC_RW_MIN 5*HZ/100 /* 50 msec */ #define IDETAPE_DSC_RW_MAX 40*HZ/100 /* 400 msec */ #define IDETAPE_DSC_RW_TIMEOUT 2*60*HZ /* 2 minutes */ @@ -176,15 +164,9 @@ enum { /*************************** End of tunable parameters ***********************/ -/* - * Read/Write error simulation - */ +/* Read/Write error simulation */ #define SIMULATE_ERRORS 0 -/* - * For general magnetic tape device compatibility. - */ - /* tape directions */ enum { IDETAPE_DIR_NONE = (1 << 0), @@ -199,24 +181,32 @@ struct idetape_bh { char *b_data; }; -/* - * Our view of a packet command. - */ typedef struct idetape_packet_command_s { - u8 c[12]; /* Actual packet bytes */ - int retries; /* On each retry, we increment retries */ - int error; /* Error code */ - int request_transfer; /* Bytes to transfer */ - int actually_transferred; /* Bytes actually transferred */ - int buffer_size; /* Size of our data buffer */ + /* Actual packet bytes */ + u8 c[12]; + /* On each retry, we increment retries */ + int retries; + /* Error code */ + int error; + /* Bytes to transfer */ + int request_transfer; + /* Bytes actually transferred */ + int actually_transferred; + /* Size of our data buffer */ + int buffer_size; struct idetape_bh *bh; char *b_data; int b_count; - u8 *buffer; /* Data buffer */ - u8 *current_position; /* Pointer into the above buffer */ - ide_startstop_t (*callback) (ide_drive_t *); /* Called when this packet command is completed */ - u8 pc_buffer[IDETAPE_PC_BUFFER_SIZE]; /* Temporary buffer */ - unsigned long flags; /* Status/Action bit flags: long for set_bit */ + /* Data buffer */ + u8 *buffer; + /* Pointer into the above buffer */ + u8 *current_position; + /* Called when this packet command is completed */ + ide_startstop_t (*callback) (ide_drive_t *); + /* Temporary buffer */ + u8 pc_buffer[IDETAPE_PC_BUFFER_SIZE]; + /* Status/Action bit flags: long for set_bit */ + unsigned long flags; } idetape_pc_t; /* @@ -235,9 +225,7 @@ typedef struct idetape_packet_command_s { /* Data direction */ #define PC_WRITING 5 -/* - * A pipeline stage. - */ +/* A pipeline stage. */ typedef struct idetape_stage_s { struct request rq; /* The corresponding request */ struct idetape_bh *bh; /* The data buffers */ @@ -245,9 +233,8 @@ typedef struct idetape_stage_s { } idetape_stage_t; /* - * Most of our global data which we need to save even as we leave the - * driver due to an interrupt or a timer event is stored in a variable - * of type idetape_tape_t, defined below. + * Most of our global data which we need to save even as we leave the driver due + * to an interrupt or a timer event is stored in the struct defined below. */ typedef struct ide_tape_obj { ide_drive_t *drive; @@ -283,15 +270,14 @@ typedef struct ide_tape_obj { int rq_stack_index; /* - * DSC polling variables. + * DSC polling variables. * - * While polling for DSC we use postponed_rq to postpone the - * current request so that ide.c will be able to service - * pending requests on the other device. Note that at most - * we will have only one DSC (usually data transfer) request - * in the device request queue. Additional requests can be - * queued in our internal pipeline, but they will be visible - * to ide.c only one at a time. + * While polling for DSC we use postponed_rq to postpone the current + * request so that ide.c will be able to service pending requests on the + * other device. Note that at most we will have only one DSC (usually + * data transfer) request in the device request queue. Additional + * requests can be queued in our internal pipeline, but they will be + * visible to ide.c only one at a time. */ struct request *postponed_rq; /* The time in which we started polling for DSC */ @@ -303,21 +289,15 @@ typedef struct ide_tape_obj { unsigned long dsc_poll_freq; unsigned long dsc_timeout; - /* - * Read position information - */ + /* Read position information */ u8 partition; /* Current block */ unsigned int first_frame; - /* - * Last error information - */ + /* Last error information */ u8 sense_key, asc, ascq; - /* - * Character device operation - */ + /* Character device operation */ unsigned int minor; /* device name */ char name[4]; @@ -332,33 +312,30 @@ typedef struct ide_tape_obj { u8 caps[20]; /* - * Active data transfer request parameters. - * - * At most, there is only one ide-tape originated data transfer - * request in the device request queue. This allows ide.c to - * easily service requests from the other device when we - * postpone our active request. In the pipelined operation - * mode, we use our internal pipeline structure to hold - * more data requests. + * Active data transfer request parameters. * - * The data buffer size is chosen based on the tape's - * recommendation. + * At most, there is only one ide-tape originated data transfer request + * in the device request queue. This allows ide.c to easily service + * requests from the other device when we postpone our active request. + * In the pipelined operation mode, we use our internal pipeline + * structure to hold more data requests. The data buffer size is chosen + * based on the tape's recommendation. */ - /* Ptr to the request which is waiting in the device request queue */ + /* ptr to the request which is waiting in the device request queue */ struct request *active_data_rq; - /* Data buffer size (chosen based on the tape's recommendation */ + /* Data buffer size chosen based on the tape's recommendation */ int stage_size; idetape_stage_t *merge_stage; int merge_stage_size; struct idetape_bh *bh; char *b_data; int b_count; - + /* - * Pipeline parameters. + * Pipeline parameters. * - * To accomplish non-pipelined mode, we simply set the following - * variables to zero (or NULL, where appropriate). + * To accomplish non-pipelined mode, we simply set the following + * variables to zero (or NULL, where appropriate). */ /* Number of currently used stages */ int nr_stages; @@ -385,9 +362,7 @@ typedef struct ide_tape_obj { /* protects the ide-tape queue */ spinlock_t lock; - /* - * Measures average tape speed - */ + /* Measures average tape speed */ unsigned long avg_time; int avg_size; int avg_speed; @@ -400,11 +375,9 @@ typedef struct ide_tape_obj { char write_prot; /* - * Limit the number of times a request can - * be postponed, to avoid an infinite postpone - * deadlock. + * Limit the number of times a request can be postponed, to avoid an + * infinite postpone deadlock. */ - /* request postpone count limit */ int postpone_cnt; /* @@ -419,18 +392,14 @@ typedef struct ide_tape_obj { int tape_head; int last_tape_head; - /* - * Speed control at the tape buffers input/output - */ + /* Speed control at the tape buffers input/output */ unsigned long insert_time; int insert_size; int insert_speed; int max_insert_speed; int measure_insert_time; - /* - * Speed regulation negative feedback loop - */ + /* Speed regulation negative feedback loop */ int speed_control; int pipeline_head_speed; int controlled_pipeline_head_speed; @@ -477,9 +446,7 @@ static void ide_tape_put(struct ide_tape_obj *tape) mutex_unlock(&idetape_ref_mutex); } -/* - * Tape door status - */ +/* Tape door status */ #define DOOR_UNLOCKED 0 #define DOOR_LOCKED 1 #define DOOR_EXPLICITLY_LOCKED 2 @@ -499,30 +466,23 @@ static void ide_tape_put(struct ide_tape_obj *tape) /* 0 = no tape is loaded, so we don't rewind after ejecting */ #define IDETAPE_MEDIUM_PRESENT 9 -/* - * Some defines for the READ BUFFER command - */ +/* A define for the READ BUFFER command */ #define IDETAPE_RETRIEVE_FAULTY_BLOCK 6 -/* - * Some defines for the SPACE command - */ +/* Some defines for the SPACE command */ #define IDETAPE_SPACE_OVER_FILEMARK 1 #define IDETAPE_SPACE_TO_EOD 3 -/* - * Some defines for the LOAD UNLOAD command - */ +/* Some defines for the LOAD UNLOAD command */ #define IDETAPE_LU_LOAD_MASK 1 #define IDETAPE_LU_RETENSION_MASK 2 #define IDETAPE_LU_EOT_MASK 4 /* - * Special requests for our block device strategy routine. + * Special requests for our block device strategy routine. * - * In order to service a character device command, we add special - * requests to the tail of our block device request queue and wait - * for their completion. + * In order to service a character device command, we add special requests to + * the tail of our block device request queue and wait for their completion. */ enum { @@ -533,10 +493,7 @@ enum { REQ_IDETAPE_READ_BUFFER = (1 << 4), }; -/* - * Error codes which are returned in rq->errors to the higher part - * of the driver. - */ +/* Error codes returned in rq->errors to the higher part of the driver. */ #define IDETAPE_ERROR_GENERAL 101 #define IDETAPE_ERROR_FILEMARK 102 #define IDETAPE_ERROR_EOD 103 @@ -560,8 +517,8 @@ struct idetape_id_gcw { #define IDETAPE_CAPABILITIES_PAGE 0x2a /* - * The variables below are used for the character device interface. - * Additional state variables are defined in our ide_drive_t structure. + * The variables below are used for the character device interface. Additional + * state variables are defined in our ide_drive_t structure. */ static struct ide_tape_obj * idetape_devs[MAX_HWIFS * MAX_DRIVES]; @@ -579,10 +536,6 @@ static struct ide_tape_obj *ide_tape_chrdev_get(unsigned int i) return tape; } -/* - * Function declarations - * - */ static int idetape_chrdev_release (struct inode *inode, struct file *filp); static void idetape_write_release (ide_drive_t *drive, unsigned int minor); @@ -711,9 +664,6 @@ static struct request *idetape_next_rq_storage (ide_drive_t *drive) return (&tape->rq_stack[tape->rq_stack_index++]); } -/* - * idetape_init_pc initializes a packet command. - */ static void idetape_init_pc (idetape_pc_t *pc) { memset(pc->c, 0, 12); @@ -809,10 +759,7 @@ static void idetape_activate_next_stage(ide_drive_t *drive) tape->next_stage = stage->next; } -/* - * idetape_kfree_stage calls kfree to completely free a stage, along with - * its related buffers. - */ +/* Free a stage along with its related buffers completely. */ static void __idetape_kfree_stage (idetape_stage_t *stage) { struct idetape_bh *prev_bh, *bh = stage->bh; @@ -840,8 +787,8 @@ static void idetape_kfree_stage (idetape_tape_t *tape, idetape_stage_t *stage) } /* - * idetape_remove_stage_head removes tape->first_stage from the pipeline. - * The caller should avoid race conditions. + * Remove tape->first_stage from the pipeline. The caller should avoid race + * conditions. */ static void idetape_remove_stage_head (ide_drive_t *drive) { @@ -899,8 +846,8 @@ static void idetape_abort_pipeline(ide_drive_t *drive, } /* - * idetape_end_request is used to finish servicing a request, and to - * insert a pending pipeline request into the main device queue. + * Finish servicing a request and insert a pending pipeline request into the + * main device queue. */ static int idetape_end_request(ide_drive_t *drive, int uptodate, int nr_sects) { @@ -951,9 +898,7 @@ static int idetape_end_request(ide_drive_t *drive, int uptodate, int nr_sects) if (tape->next_stage != NULL) { idetape_activate_next_stage(drive); - /* - * Insert the next request into the request queue. - */ + /* Insert the next request into the request queue. */ (void)ide_do_drive_cmd(drive, tape->active_data_rq, ide_end); } else if (!error) { @@ -1020,23 +965,19 @@ static void idetape_init_rq(struct request *rq, u8 cmd) } /* - * idetape_queue_pc_head generates a new packet command request in front - * of the request queue, before the current request, so that it will be - * processed immediately, on the next pass through the driver. - * - * idetape_queue_pc_head is called from the request handling part of - * the driver (the "bottom" part). Safe storage for the request should - * be allocated with idetape_next_pc_storage and idetape_next_rq_storage - * before calling idetape_queue_pc_head. + * Generate a new packet command request in front of the request queue, before + * the current request, so that it will be processed immediately, on the next + * pass through the driver. The function below is called from the request + * handling part of the driver (the "bottom" part). Safe storage for the request + * should be allocated with ide_tape_next_{pc,rq}_storage() prior to that. * - * Memory for those requests is pre-allocated at initialization time, and - * is limited to IDETAPE_PC_STACK requests. We assume that we have enough - * space for the maximum possible number of inter-dependent packet commands. + * Memory for those requests is pre-allocated at initialization time, and is + * limited to IDETAPE_PC_STACK requests. We assume that we have enough space for + * the maximum possible number of inter-dependent packet commands. * - * The higher level of the driver - The ioctl handler and the character - * device handling functions should queue request to the lower level part - * and wait for their completion using idetape_queue_pc_tail or - * idetape_queue_rw_tail. + * The higher level of the driver - The ioctl handler and the character device + * handling functions should queue request to the lower level part and wait for + * their completion using idetape_queue_pc_tail or idetape_queue_rw_tail. */ static void idetape_queue_pc_head (ide_drive_t *drive, idetape_pc_t *pc,struct request *rq) { @@ -1069,9 +1010,8 @@ static ide_startstop_t idetape_retry_pc (ide_drive_t *drive) } /* - * idetape_postpone_request postpones the current request so that - * ide.c will be able to service requests from another device on - * the same hwgroup while we are polling for DSC. + * Postpone the current request so that ide.c will be able to service requests + * from another device on the same hwgroup while we are polling for DSC. */ static void idetape_postpone_request (ide_drive_t *drive) { @@ -1258,46 +1198,40 @@ static ide_startstop_t idetape_pc_intr(ide_drive_t *drive) } /* - * Packet Command Interface + * Packet Command Interface * - * The current Packet Command is available in tape->pc, and will not - * change until we finish handling it. Each packet command is associated - * with a callback function that will be called when the command is - * finished. + * The current Packet Command is available in tape->pc, and will not change + * until we finish handling it. Each packet command is associated with a + * callback function that will be called when the command is finished. * - * The handling will be done in three stages: + * The handling will be done in three stages: * - * 1. idetape_issue_pc will send the packet command to the - * drive, and will set the interrupt handler to idetape_pc_intr. + * 1. idetape_issue_pc will send the packet command to the drive, and will set + * the interrupt handler to idetape_pc_intr. * - * 2. On each interrupt, idetape_pc_intr will be called. This step - * will be repeated until the device signals us that no more - * interrupts will be issued. + * 2. On each interrupt, idetape_pc_intr will be called. This step will be + * repeated until the device signals us that no more interrupts will be issued. * - * 3. ATAPI Tape media access commands have immediate status with a - * delayed process. In case of a successful initiation of a - * media access packet command, the DSC bit will be set when the - * actual execution of the command is finished. - * Since the tape drive will not issue an interrupt, we have to - * poll for this event. In this case, we define the request as - * "low priority request" by setting rq_status to - * IDETAPE_RQ_POSTPONED, set a timer to poll for DSC and exit - * the driver. + * 3. ATAPI Tape media access commands have immediate status with a delayed + * process. In case of a successful initiation of a media access packet command, + * the DSC bit will be set when the actual execution of the command is finished. + * Since the tape drive will not issue an interrupt, we have to poll for this + * event. In this case, we define the request as "low priority request" by + * setting rq_status to IDETAPE_RQ_POSTPONED, set a timer to poll for DSC and + * exit the driver. * - * ide.c will then give higher priority to requests which - * originate from the other device, until will change rq_status - * to RQ_ACTIVE. + * ide.c will then give higher priority to requests which originate from the + * other device, until will change rq_status to RQ_ACTIVE. * - * 4. When the packet command is finished, it will be checked for errors. + * 4. When the packet command is finished, it will be checked for errors. * - * 5. In case an error was found, we queue a request sense packet - * command in front of the request queue and retry the operation - * up to IDETAPE_MAX_PC_RETRIES times. - * - * 6. In case no error was found, or we decided to give up and not - * to retry again, the callback function will be called and then - * we will handle the next request. + * 5. In case an error was found, we queue a request sense packet command in + * front of the request queue and retry the operation up to + * IDETAPE_MAX_PC_RETRIES times. * + * 6. In case no error was found, or we decided to give up and not to retry + * again, the callback function will be called and then we will handle the next + * request. */ static ide_startstop_t idetape_transfer_pc(ide_drive_t *drive) { @@ -1363,9 +1297,9 @@ static ide_startstop_t idetape_issue_pc(ide_drive_t *drive, idetape_pc_t *pc) if (pc->retries > IDETAPE_MAX_PC_RETRIES || test_bit(PC_ABORT, &pc->flags)) { /* - * We will "abort" retrying a packet command in case - * a legitimate error code was received (crossing a - * filemark, or end of the media, for example). + * We will "abort" retrying a packet command in case legitimate + * error code was received (crossing a filemark, or end of the + * media, for example). */ if (!test_bit(PC_ABORT, &pc->flags)) { if (!(pc->c[0] == TEST_UNIT_READY && @@ -1416,9 +1350,6 @@ static ide_startstop_t idetape_issue_pc(ide_drive_t *drive, idetape_pc_t *pc) } } -/* - * General packet command callback function. - */ static ide_startstop_t idetape_pc_callback (ide_drive_t *drive) { idetape_tape_t *tape = drive->driver_data; @@ -1429,15 +1360,14 @@ static ide_startstop_t idetape_pc_callback (ide_drive_t *drive) return ide_stopped; } -/* - * A mode sense command is used to "sense" tape parameters. - */ +/* A mode sense command is used to "sense" tape parameters. */ static void idetape_create_mode_sense_cmd (idetape_pc_t *pc, u8 page_code) { idetape_init_pc(pc); pc->c[0] = MODE_SENSE; if (page_code != IDETAPE_BLOCK_DESCRIPTOR) - pc->c[1] = 8; /* DBD = 1 - Don't return block descriptors */ + /* DBD = 1 - Don't return block descriptors */ + pc->c[1] = 8; pc->c[2] = page_code; /* * Changed pc->c[3] to 0 (255 will at best return unused info). @@ -1447,7 +1377,8 @@ static void idetape_create_mode_sense_cmd (idetape_pc_t *pc, u8 page_code) * and return an error when 255 is used. */ pc->c[3] = 0; - pc->c[4] = 255; /* (We will just discard data in that case) */ + /* We will just discard data in that case */ + pc->c[4] = 255; if (page_code == IDETAPE_BLOCK_DESCRIPTOR) pc->request_transfer = 12; else if (page_code == IDETAPE_CAPABILITIES_PAGE) @@ -1619,9 +1550,6 @@ static void idetape_create_write_cmd(idetape_tape_t *tape, idetape_pc_t *pc, uns set_bit(PC_DMA_RECOMMENDED, &pc->flags); } -/* - * idetape_do_request is our request handling function. - */ static ide_startstop_t idetape_do_request(ide_drive_t *drive, struct request *rq, sector_t block) { @@ -1635,18 +1563,14 @@ static ide_startstop_t idetape_do_request(ide_drive_t *drive, rq->sector, rq->nr_sectors, rq->current_nr_sectors); if (!blk_special_request(rq)) { - /* - * We do not support buffer cache originated requests. - */ + /* We do not support buffer cache originated requests. */ printk(KERN_NOTICE "ide-tape: %s: Unsupported request in " "request queue (%d)\n", drive->name, rq->cmd_type); ide_end_request(drive, 0, 0); return ide_stopped; } - /* - * Retry a failed packet command - */ + /* Retry a failed packet command */ if (tape->failed_pc != NULL && tape->pc->c[0] == REQUEST_SENSE) { return idetape_issue_pc(drive, tape->failed_pc); @@ -1733,9 +1657,7 @@ out: return idetape_issue_pc(drive, pc); } -/* - * Pipeline related functions - */ +/* Pipeline related functions */ static inline int idetape_pipeline_active (idetape_tape_t *tape) { int rc1, rc2; @@ -1746,16 +1668,16 @@ static inline int idetape_pipeline_active (idetape_tape_t *tape) } /* - * idetape_kmalloc_stage uses __get_free_page to allocate a pipeline - * stage, along with all the necessary small buffers which together make - * a buffer of size tape->stage_size (or a bit more). We attempt to - * combine sequential pages as much as possible. + * The function below uses __get_free_page to allocate a pipeline stage, along + * with all the necessary small buffers which together make a buffer of size + * tape->stage_size (or a bit more). We attempt to combine sequential pages as + * much as possible. * - * Returns a pointer to the new allocated stage, or NULL if we - * can't (or don't want to) allocate a stage. + * It returns a pointer to the new allocated stage, or NULL if we can't (or + * don't want to) allocate a stage. * - * Pipeline stages are optional and are used to increase performance. - * If we can't allocate them, we'll manage without them. + * Pipeline stages are optional and are used to increase performance. If we + * can't allocate them, we'll manage without them. */ static idetape_stage_t *__idetape_kmalloc_stage (idetape_tape_t *tape, int full, int clear) { @@ -1913,9 +1835,7 @@ static void idetape_switch_buffers (idetape_tape_t *tape, idetape_stage_t *stage idetape_init_merge_stage(tape); } -/* - * idetape_add_stage_tail adds a new stage at the end of the pipeline. - */ +/* Add a new stage at the end of the pipeline. */ static void idetape_add_stage_tail (ide_drive_t *drive,idetape_stage_t *stage) { idetape_tape_t *tape = drive->driver_data; @@ -1937,12 +1857,9 @@ static void idetape_add_stage_tail (ide_drive_t *drive,idetape_stage_t *stage) spin_unlock_irqrestore(&tape->lock, flags); } -/* - * idetape_wait_for_request installs a completion in a pending request - * and sleeps until it is serviced. - * - * The caller should ensure that the request will not be serviced - * before we install the completion (usually by disabling interrupts). +/* Install a completion in a pending request and sleep until it is serviced. The + * caller should ensure that the request will not be serviced before we install + * the completion (usually by disabling interrupts). */ static void idetape_wait_for_request (ide_drive_t *drive, struct request *rq) { @@ -1996,12 +1913,8 @@ static ide_startstop_t idetape_read_position_callback(ide_drive_t *drive) } /* - * idetape_create_write_filemark_cmd will: - * - * 1. Write a filemark if write_filemark=1. - * 2. Flush the device buffers without writing a filemark - * if write_filemark=0. - * + * Write a filemark if write_filemark=1. Flush the device buffers without + * writing a filemark otherwise. */ static void idetape_create_write_filemark_cmd (ide_drive_t *drive, idetape_pc_t *pc,int write_filemark) { @@ -2020,24 +1933,17 @@ static void idetape_create_test_unit_ready_cmd(idetape_pc_t *pc) } /* - * idetape_queue_pc_tail is based on the following functions: - * - * ide_do_drive_cmd from ide.c - * cdrom_queue_request and cdrom_queue_packet_command from ide-cd.c - * - * We add a special packet command request to the tail of the request - * queue, and wait for it to be serviced. + * We add a special packet command request to the tail of the request queue, and + * wait for it to be serviced. This is not to be called from within the request + * handling part of the driver! We allocate here data on the stack and it is + * valid until the request is finished. This is not the case for the bottom part + * of the driver, where we are always leaving the functions to wait for an + * interrupt or a timer event. * - * This is not to be called from within the request handling part - * of the driver ! We allocate here data in the stack, and it is valid - * until the request is finished. This is not the case for the bottom - * part of the driver, where we are always leaving the functions to wait - * for an interrupt or a timer event. - * - * From the bottom part of the driver, we should allocate safe memory - * using idetape_next_pc_storage and idetape_next_rq_storage, and add - * the request to the request list without waiting for it to be serviced ! - * In that case, we usually use idetape_queue_pc_head. + * From the bottom part of the driver, we should allocate safe memory using + * idetape_next_pc_storage() and ide_tape_next_rq_storage(), and add the request + * to the request list without waiting for it to be serviced! In that case, we + * usually use idetape_queue_pc_head(). */ static int __idetape_queue_pc_tail (ide_drive_t *drive, idetape_pc_t *pc) { @@ -2065,9 +1971,7 @@ static int idetape_wait_ready(ide_drive_t *drive, unsigned long timeout) idetape_pc_t pc; int load_attempted = 0; - /* - * Wait for the tape to become ready - */ + /* Wait for the tape to become ready */ set_bit(IDETAPE_MEDIUM_PRESENT, &tape->flags); timeout += jiffies; while (time_before(jiffies, timeout)) { @@ -2075,7 +1979,8 @@ static int idetape_wait_ready(ide_drive_t *drive, unsigned long timeout) if (!__idetape_queue_pc_tail(drive, &pc)) return 0; if ((tape->sense_key == 2 && tape->asc == 4 && tape->ascq == 2) - || (tape->asc == 0x3A)) { /* no media */ + || (tape->asc == 0x3A)) { + /* no media */ if (load_attempted) return -ENOMEDIUM; idetape_create_load_unload_cmd(drive, &pc, IDETAPE_LU_LOAD_MASK); @@ -2203,13 +2108,10 @@ static int __idetape_discard_read_pipeline (ide_drive_t *drive) } /* - * idetape_position_tape positions the tape to the requested block - * using the LOCATE packet command. A READ POSITION command is then - * issued to check where we are positioned. - * - * Like all higher level operations, we queue the commands at the tail - * of the request queue and wait for their completion. - * + * Position the tape to the requested block using the LOCATE packet command. + * A READ POSITION command is then issued to check where we are positioned. Like + * all higher level operations, we queue the commands at the tail of the request + * queue and wait for their completion. */ static int idetape_position_tape (ide_drive_t *drive, unsigned int block, u8 partition, int skip) { @@ -2247,8 +2149,8 @@ static void idetape_discard_read_pipeline (ide_drive_t *drive, int restore_posit } /* - * idetape_queue_rw_tail generates a read/write request for the block - * device interface and wait for it to be serviced. + * Generate a read/write request for the block device interface and wait for it + * to be serviced. */ static int idetape_queue_rw_tail(ide_drive_t *drive, int cmd, int blocks, struct idetape_bh *bh) { @@ -2343,15 +2245,15 @@ static void idetape_wait_first_stage (ide_drive_t *drive) } /* - * idetape_add_chrdev_write_request tries to add a character device - * originated write request to our pipeline. In case we don't succeed, - * we revert to non-pipelined operation mode for this request. + * Try to add a character device originated write request to our pipeline. In + * case we don't succeed, we revert to non-pipelined operation mode for this + * request. In order to accomplish that, we * - * 1. Try to allocate a new pipeline stage. - * 2. If we can't, wait for more and more requests to be serviced - * and try again each time. - * 3. If we still can't allocate a stage, fallback to - * non-pipelined operation mode for this request. + * 1. Try to allocate a new pipeline stage. + * 2. If we can't, wait for more and more requests to be serviced and try again + * each time. + * 3. If we still can't allocate a stage, fallback to non-pipelined operation + * mode for this request. */ static int idetape_add_chrdev_write_request (ide_drive_t *drive, int blocks) { @@ -2362,10 +2264,7 @@ static int idetape_add_chrdev_write_request (ide_drive_t *drive, int blocks) debug_log(DBG_CHRDEV, "Enter %s\n", __func__); - /* - * Attempt to allocate a new stage. - * Pay special attention to possible race conditions. - */ + /* Attempt to allocate a new stage. Beware possible race conditions. */ while ((new_stage = idetape_kmalloc_stage(tape)) == NULL) { spin_lock_irqsave(&tape->lock, flags); if (idetape_pipeline_active(tape)) { @@ -2377,8 +2276,8 @@ static int idetape_add_chrdev_write_request (ide_drive_t *drive, int blocks) if (idetape_pipeline_active(tape)) continue; /* - * Linux is short on memory. Fallback to - * non-pipelined operation mode for this request. + * The machine is short on memory. Fallback to non- + * pipelined operation mode for this request. */ return idetape_queue_rw_tail(drive, REQ_IDETAPE_WRITE, blocks, tape->merge_stage->bh); } @@ -2395,11 +2294,11 @@ static int idetape_add_chrdev_write_request (ide_drive_t *drive, int blocks) idetape_calculate_speeds(drive); /* - * Estimate whether the tape has stopped writing by checking - * if our write pipeline is currently empty. If we are not - * writing anymore, wait for the pipeline to be full enough - * (90%) before starting to service requests, so that we will - * be able to keep up with the higher speeds of the tape. + * Estimate whether the tape has stopped writing by checking if our + * write pipeline is currently empty. If we are not writing anymore, + * wait for the pipeline to be almost completely full (90%) before + * starting to service requests, so that we will be able to keep up with + * the higher speeds of the tape. */ if (!idetape_pipeline_active(tape)) { if (tape->nr_stages >= tape->max_stages * 9 / 10 || @@ -2420,8 +2319,8 @@ static int idetape_add_chrdev_write_request (ide_drive_t *drive, int blocks) } /* - * idetape_wait_for_pipeline will wait until all pending pipeline - * requests are serviced. Typically called on device close. + * Wait until all pending pipeline requests are serviced. Typically called on + * device close. */ static void idetape_wait_for_pipeline (ide_drive_t *drive) { @@ -2490,10 +2389,10 @@ static void idetape_empty_write_pipeline (ide_drive_t *drive) tape->chrdev_dir = IDETAPE_DIR_NONE; /* - * On the next backup, perform the feedback loop again. - * (I don't want to keep sense information between backups, - * as some systems are constantly on, and the system load - * can be totally different on the next backup). + * On the next backup, perform the feedback loop again. (I don't want to + * keep sense information between backups, as some systems are + * constantly on, and the system load can be totally different on the + * next backup). */ tape->max_stages = tape->min_pipeline; if (tape->first_stage != NULL || @@ -2545,11 +2444,10 @@ static int idetape_init_read(ide_drive_t *drive, int max_stages) tape->chrdev_dir = IDETAPE_DIR_READ; /* - * Issue a read 0 command to ensure that DSC handshake - * is switched from completion mode to buffer available - * mode. - * No point in issuing this if DSC overlap isn't supported, - * some drives (Seagate STT3401A) will return an error. + * Issue a read 0 command to ensure that DSC handshake is + * switched from completion mode to buffer available mode. + * No point in issuing this if DSC overlap isn't supported, some + * drives (Seagate STT3401A) will return an error. */ if (drive->dsc_overlap) { bytes_read = idetape_queue_rw_tail(drive, REQ_IDETAPE_READ, 0, tape->merge_stage->bh); @@ -2590,9 +2488,8 @@ static int idetape_init_read(ide_drive_t *drive, int max_stages) } /* - * idetape_add_chrdev_read_request is called from idetape_chrdev_read - * to service a character device read request and add read-ahead - * requests to our pipeline. + * Called from idetape_chrdev_read() to service a character device read request + * and add read-ahead requests to our pipeline. */ static int idetape_add_chrdev_read_request (ide_drive_t *drive,int blocks) { @@ -2603,16 +2500,11 @@ static int idetape_add_chrdev_read_request (ide_drive_t *drive,int blocks) debug_log(DBG_PROCS, "Enter %s, %d blocks\n", __func__, blocks); - /* - * If we are at a filemark, return a read length of 0 - */ + /* If we are at a filemark, return a read length of 0 */ if (test_bit(IDETAPE_FILEMARK, &tape->flags)) return 0; - /* - * Wait for the next block to be available at the head - * of the pipeline - */ + /* Wait for the next block to reach the head of the pipeline. */ idetape_init_read(drive, tape->max_stages); if (tape->first_stage == NULL) { if (test_bit(IDETAPE_PIPELINE_ERROR, &tape->flags)) @@ -2651,7 +2543,7 @@ static void idetape_pad_zeros (ide_drive_t *drive, int bcount) idetape_tape_t *tape = drive->driver_data; struct idetape_bh *bh; int blocks; - + while (bcount) { unsigned int count; @@ -2691,10 +2583,9 @@ static int idetape_pipeline_size (ide_drive_t *drive) } /* - * Rewinds the tape to the Beginning Of the current Partition (BOP). - * - * We currently support only one partition. - */ + * Rewinds the tape to the Beginning Of the current Partition (BOP). We + * currently support only one partition. + */ static int idetape_rewind_tape (ide_drive_t *drive) { int retval; @@ -2716,13 +2607,7 @@ static int idetape_rewind_tape (ide_drive_t *drive) return 0; } -/* - * Our special ide-tape ioctl's. - * - * Currently there aren't any ioctl's. - * mtio.h compatible commands should be issued to the character device - * interface. - */ +/* mtio.h compatible commands should be issued to the chrdev interface. */ static int idetape_blkdev_ioctl(ide_drive_t *drive, unsigned int cmd, unsigned long arg) { idetape_tape_t *tape = drive->driver_data; @@ -2756,13 +2641,11 @@ static int idetape_blkdev_ioctl(ide_drive_t *drive, unsigned int cmd, unsigned l } /* - * idetape_space_over_filemarks is now a bit more complicated than just - * passing the command to the tape since we may have crossed some - * filemarks during our pipelined read-ahead mode. - * - * As a minor side effect, the pipeline enables us to support MTFSFM when - * the filemark is in our internal pipeline even if the tape doesn't - * support spacing over filemarks in the reverse direction. + * The function below is now a bit more complicated than just passing the + * command to the tape since we may have crossed some filemarks during our + * pipelined read-ahead mode. As a minor side effect, the pipeline enables us to + * support MTFSFM when the filemark is in our internal pipeline even if the tape + * doesn't support spacing over filemarks in the reverse direction. */ static int idetape_space_over_filemarks (ide_drive_t *drive,short mt_op,int mt_count) { @@ -2781,10 +2664,7 @@ static int idetape_space_over_filemarks (ide_drive_t *drive,short mt_op,int mt_c } if (tape->chrdev_dir == IDETAPE_DIR_READ) { - /* - * We have a read-ahead buffer. Scan it for crossed - * filemarks. - */ + /* its a read-ahead buffer, scan it for crossed filemarks. */ tape->merge_stage_size = 0; if (test_and_clear_bit(IDETAPE_FILEMARK, &tape->flags)) ++count; @@ -2797,13 +2677,15 @@ static int idetape_space_over_filemarks (ide_drive_t *drive,short mt_op,int mt_c spin_lock_irqsave(&tape->lock, flags); if (tape->first_stage == tape->active_stage) { /* - * We have reached the active stage in the read pipeline. - * There is no point in allowing the drive to continue - * reading any farther, so we stop the pipeline. + * We have reached the active stage in the read + * pipeline. There is no point in allowing the + * drive to continue reading any farther, so we + * stop the pipeline. * - * This section should be moved to a separate subroutine, - * because a similar function is performed in - * __idetape_discard_read_pipeline(), for example. + * This section should be moved to a separate + * subroutine because similar operations are + * done in __idetape_discard_read_pipeline(), + * for example. */ tape->next_stage = NULL; spin_unlock_irqrestore(&tape->lock, flags); @@ -2819,8 +2701,8 @@ static int idetape_space_over_filemarks (ide_drive_t *drive,short mt_op,int mt_c } /* - * The filemark was not found in our internal pipeline. - * Now we can issue the space command. + * The filemark was not found in our internal pipeline; now we can issue + * the space command. */ switch (mt_op) { case MTFSF: @@ -2843,21 +2725,19 @@ static int idetape_space_over_filemarks (ide_drive_t *drive,short mt_op,int mt_c /* - * Our character device read / write functions. + * Our character device read / write functions. * - * The tape is optimized to maximize throughput when it is transferring - * an integral number of the "continuous transfer limit", which is - * a parameter of the specific tape (26 KB on my particular tape). - * (32 kB for Onstream) + * The tape is optimized to maximize throughput when it is transferring an + * integral number of the "continuous transfer limit", which is a parameter of + * the specific tape (26kB on my particular tape, 32kB for Onstream). * - * As of version 1.3 of the driver, the character device provides an - * abstract continuous view of the media - any mix of block sizes (even 1 - * byte) on the same backup/restore procedure is supported. The driver - * will internally convert the requests to the recommended transfer unit, - * so that an unmatch between the user's block size to the recommended - * size will only result in a (slightly) increased driver overhead, but - * will no longer hit performance. - * This is not applicable to Onstream. + * As of version 1.3 of the driver, the character device provides an abstract + * continuous view of the media - any mix of block sizes (even 1 byte) on the + * same backup/restore procedure is supported. The driver will internally + * convert the requests to the recommended transfer unit, so that an unmatch + * between the user's block size to the recommended size will only result in a + * (slightly) increased driver overhead, but will no longer hit performance. + * This is not applicable to Onstream. */ static ssize_t idetape_chrdev_read (struct file *file, char __user *buf, size_t count, loff_t *ppos) @@ -2950,11 +2830,10 @@ static ssize_t idetape_chrdev_write (struct file *file, const char __user *buf, idetape_init_merge_stage(tape); /* - * Issue a write 0 command to ensure that DSC handshake - * is switched from completion mode to buffer available - * mode. - * No point in issuing this if DSC overlap isn't supported, - * some drives (Seagate STT3401A) will return an error. + * Issue a write 0 command to ensure that DSC handshake is + * switched from completion mode to buffer available mode. No + * point in issuing this if DSC overlap isn't supported, some + * drives (Seagate STT3401A) will return an error. */ if (drive->dsc_overlap) { ssize_t retval = idetape_queue_rw_tail(drive, REQ_IDETAPE_WRITE, 0, tape->merge_stage->bh); @@ -3045,9 +2924,7 @@ static int idetape_mtioctop(ide_drive_t *drive, short mt_op, int mt_count) debug_log(DBG_ERR, "Handling MTIOCTOP ioctl: mt_op=%d, mt_count=%d\n", mt_op, mt_count); - /* - * Commands which need our pipelined read-ahead stages. - */ + /* Commands which need our pipelined read-ahead stages. */ switch (mt_op) { case MTFSF: case MTFSFM: @@ -3235,9 +3112,6 @@ static void ide_tape_get_bsize_from_bdesc(ide_drive_t *drive) tape->drv_write_prot = (pc.buffer[2] & 0x80) >> 7; } -/* - * Our character device open function. - */ static int idetape_chrdev_open (struct inode *inode, struct file *filp) { unsigned int minor = iminor(inode), i = minor & ~0xc0; @@ -3304,9 +3178,7 @@ static int idetape_chrdev_open (struct inode *inode, struct file *filp) } } - /* - * Lock the tape drive door so user can't eject. - */ + /* Lock the tape drive door so user can't eject. */ if (tape->chrdev_dir == IDETAPE_DIR_NONE) { if (idetape_create_prevent_cmd(drive, &pc, 1)) { if (!idetape_queue_pc_tail(drive, &pc)) { @@ -3341,9 +3213,6 @@ static void idetape_write_release (ide_drive_t *drive, unsigned int minor) idetape_flush_tape_buffers(drive); } -/* - * Our character device release function. - */ static int idetape_chrdev_release (struct inode *inode, struct file *filp) { struct ide_tape_obj *tape = ide_tape_f(filp); @@ -3500,9 +3369,6 @@ static void idetape_add_settings (ide_drive_t *drive) { idetape_tape_t *tape = drive->driver_data; -/* - * drive setting name read/write data type min max mul_factor div_factor data pointer set function - */ ide_add_setting(drive, "buffer", SETTING_READ, TYPE_SHORT, 0, 0xffff, 1, 2, (u16 *)&tape->caps[16], NULL); ide_add_setting(drive, "pipeline_min", SETTING_RW, TYPE_INT, 1, 0xffff, tape->stage_size / 1024, 1, &tape->min_pipeline, NULL); @@ -3529,16 +3395,15 @@ static inline void idetape_add_settings(ide_drive_t *drive) { ; } #endif /* - * ide_setup is called to: + * The function below is called to: * - * 1. Initialize our various state variables. - * 2. Ask the tape for its capabilities. - * 3. Allocate a buffer which will be used for data - * transfer. The buffer size is chosen based on - * the recommendation which we received in step (2). + * 1. Initialize our various state variables. + * 2. Ask the tape for its capabilities. + * 3. Allocate a buffer which will be used for data transfer. The buffer size + * is chosen based on the recommendation which we received in step 2. * - * Note that at this point ide.c already assigned us an irq, so that - * we can queue requests here and wait for their completion. + * Note that at this point ide.c already assigned us an irq, so that we can + * queue requests here and wait for their completion. */ static void idetape_setup (ide_drive_t *drive, idetape_tape_t *tape, int minor) { @@ -3572,7 +3437,7 @@ static void idetape_setup (ide_drive_t *drive, idetape_tape_t *tape, int minor) set_bit(IDETAPE_DRQ_INTERRUPT, &tape->flags); tape->min_pipeline = tape->max_pipeline = tape->max_stages = 10; - + idetape_get_inquiry_results(drive); idetape_get_mode_sense_results(drive); ide_tape_get_bsize_from_bdesc(drive); @@ -3595,9 +3460,7 @@ static void idetape_setup (ide_drive_t *drive, idetape_tape_t *tape, int minor) tape->max_stages = speed * 1000 * 10 / tape->stage_size; - /* - * Limit memory use for pipeline to 10% of physical memory - */ + /* Limit memory use for pipeline to 10% of physical memory */ si_meminfo(&si); if (tape->max_stages * tape->stage_size > si.totalram * si.mem_unit / 10) tape->max_stages = si.totalram * si.mem_unit / (10 * tape->stage_size); @@ -3617,8 +3480,8 @@ static void idetape_setup (ide_drive_t *drive, idetape_tape_t *tape, int minor) t = t1; /* - * Ensure that the number we got makes sense; limit - * it within IDETAPE_DSC_RW_MIN and IDETAPE_DSC_RW_MAX. + * Ensure that the number we got makes sense; limit it within + * IDETAPE_DSC_RW_MIN and IDETAPE_DSC_RW_MAX. */ tape->best_dsc_rw_freq = max_t(unsigned long, min_t(unsigned long, t, IDETAPE_DSC_RW_MAX), @@ -3706,9 +3569,7 @@ static ide_driver_t idetape_driver = { #endif }; -/* - * Our character device supporting functions, passed to register_chrdev. - */ +/* Our character device supporting functions, passed to register_chrdev. */ static const struct file_operations idetape_fops = { .owner = THIS_MODULE, .read = idetape_chrdev_read, |