[Libburn] Erase patch
Tiago Cogumbreiro
cogumbreiro@linus.uac.pt
Thu, 04 Dec 2003 14:47:48 -0100
--=-pIRI6xUk7jKcwMEBXSSK
Content-Type: text/plain
Content-Transfer-Encoding: 7bit
Here is the patch i told you i would do, it simply adds more types of
blanking operations it doesn't include 2 modes:
- Blank a track: because it needs an argument
- Blank a track tail: only used for packet writing
PS: this diff already includes the alterations i did in the last mail
i've sent about blanking progress
--=-pIRI6xUk7jKcwMEBXSSK
Content-Disposition: attachment; filename=blank_enum.diff
Content-Type: text/x-patch; name=blank_enum.diff; charset=ISO-8859-1
Content-Transfer-Encoding: 7bit
Index: libburn/async.c
===================================================================
RCS file: /cvs/burn/burn/libburn/async.c,v
retrieving revision 1.9
diff -p -u -r1.9 async.c
--- libburn/async.c 2 Dec 2003 02:53:48 -0000 1.9
+++ libburn/async.c 4 Dec 2003 15:41:46 -0000
@@ -25,7 +25,7 @@ struct scan_opts
struct erase_opts
{
struct drive *drive;
- int fast;
+ enum libburn_erase_types type;
};
struct write_opts
@@ -133,12 +133,12 @@ int libburn_drive_scan(struct libburn_dr
static void* erase_worker_func(struct w_list *w)
{
- libburn_erase_disc_sync(w->u.erase.drive, w->u.erase.fast);
+ libburn_erase_disc_sync(w->u.erase.drive, w->u.erase.type);
remove_worker(pthread_self());
return NULL;
}
-void libburn_erase_disc(struct drive *drive, int fast)
+void libburn_erase_disc(struct drive *drive, enum libburn_erase_types type)
{
struct erase_opts o;
@@ -147,7 +147,7 @@ void libburn_erase_disc(struct drive *dr
assert(!find_worker(drive));
o.drive = drive;
- o.fast = fast;
+ o.type = type;
add_worker(drive, (WorkerFunc) erase_worker_func, &o);
}
Index: libburn/drive.c
===================================================================
RCS file: /cvs/burn/burn/libburn/drive.c,v
retrieving revision 1.228
diff -p -u -r1.228 drive.c
--- libburn/drive.c 2 Dec 2003 03:04:16 -0000 1.228
+++ libburn/drive.c 4 Dec 2003 15:41:46 -0000
@@ -143,8 +143,11 @@ void libburn_wait_all()
}
}
-void libburn_erase_disc_sync(struct drive *d, int fast)
+void libburn_erase_disc_sync(struct drive *d, enum libburn_erase_types type)
{
+ struct buffer buf;
+ int started = 0;
+
libburn_message_clear_queue();
libburn_print(1, "erasing drive %s %s\n", d->idata->vendor,
@@ -152,10 +155,24 @@ void libburn_erase_disc_sync(struct driv
if (d->status != LIBBURN_STATUS_FULL)
return;
-
d->cancel = 0;
d->busy = LIBBURN_BUSY_ERASING;
- d->erase(d, fast);
+ d->erase(d, type);
+ /* We might have a problem with fast blanking discs
+ * if the blanking lasts less then half a second we won't ever know
+ * if it started, thus we'll never know if it'll end.
+ * This will never happen because drives are slow.
+ */
+ do {
+ /* we'll check if the drive is still blanking
+ * in 1/2 second interval
+ */
+ usleep(500);
+ d->request_sense(d, &buf);
+ if(!started && buf.data[16] != 0 && buf.data[17] != 0)
+ started = 1;
+ } while(!started || buf.data[16] != 0 || buf.data[17] != 0);
+
d->busy = LIBBURN_BUSY_NO;
}
@@ -168,6 +185,21 @@ enum libburn_drive_status libburn_drive_
int libburn_drive_get_busy(struct drive *d, struct libburn_progress *p)
{
if (p) {
+ if(d->busy == LIBBURN_BUSY_ERASING) {
+ struct buffer *buf = malloc(sizeof(struct buffer));
+ p->session = 1;
+ p->sessions = 1;
+ p->track = 1;
+ p->tracks = 1;
+ p->index = 1;
+ p->indices = 1;
+ p->abs_sectors = 0x10000;
+ p->rel_sectors = 0x10000;
+ d->request_sense(d, buf);
+ p->abs_sector = (buf->data[16] << 8) | buf->data[17];
+ p->rel_sector = p->abs_sector;
+ free(buf);
+ }
/* this is where we do stuff! */
}
return d->busy != LIBBURN_BUSY_NO;
Index: libburn/drive.h
===================================================================
RCS file: /cvs/burn/burn/libburn/drive.h,v
retrieving revision 1.75
diff -p -u -r1.75 drive.h
--- libburn/drive.h 28 Nov 2003 05:05:22 -0000 1.75
+++ libburn/drive.h 4 Dec 2003 15:41:47 -0000
@@ -67,6 +67,6 @@ void libburn_send_toc(struct drive *d, s
int libburn_drive_scan_sync(struct libburn_drive_info *drives[],
unsigned int *n_drives);
-void libburn_erase_disc_sync(struct drive *d, int fast);
+void libburn_erase_disc_sync(struct drive *d, enum libburn_erase_types type);
#endif /* __DRIVE */
Index: libburn/libburn.h
===================================================================
RCS file: /cvs/burn/burn/libburn/libburn.h,v
retrieving revision 1.152
diff -p -u -r1.152 libburn.h
--- libburn/libburn.h 2 Dec 2003 04:49:18 -0000 1.152
+++ libburn/libburn.h 4 Dec 2003 15:41:48 -0000
@@ -133,6 +133,24 @@ enum libburn_track_types
LIBBURN_MODE_RAW_DATA
};
+/** Types of erasing media */
+enum libburn_erase_types
+{
+ /** Erase the entire disc */
+ LIBBURN_ERASE_FULL = 0,
+ /** Minimally blank the disc */
+ LIBBURN_ERASE_MINIMAL = 1,
+ /** All the data in the last track in the incomplete
+ * session shall be erased
+ */
+ LIBBURN_ERASE_UNRESERVE_TRACK = 3,
+ /** The Lead-In and Lead-Out of the last complete
+ * session shall be blanked */
+ LIBBURN_ERASE_UNCLOSE_SESSION = 5,
+ /** Blank the last non-empty session */
+ LIBBURN_ERASE_BLANK_SESSION = 6
+};
+
/** Possible status' of the drive in regard to the disc in it. */
enum libburn_drive_status
{
@@ -495,10 +513,9 @@ void libburn_read_opts_free(struct libbu
cancellable, as control of the operation is passed wholly to the drive and
there is no way to interrupt it safely.
@param drive The drive with which to erase a disc.
- @param fast Nonzero to do a fast erase, where only the disc's headers are
- erased; zero to erase the entire disc.
+ @param type The type of erase operatin to perform (see also libburn_erase_types)
*/
-void libburn_erase_disc(struct drive *drive, int fast);
+void libburn_erase_disc(struct drive *drive, enum libburn_erase_types type);
/** Read a disc from the drive and write it to an fd pair. The drive must be
grabbed successfully BEFORE calling this function. Always ensure that the
Index: libburn/mmc.c
===================================================================
RCS file: /cvs/burn/burn/libburn/mmc.c,v
retrieving revision 1.114
diff -p -u -r1.114 mmc.c
--- libburn/mmc.c 2 Dec 2003 02:23:29 -0000 1.114
+++ libburn/mmc.c 4 Dec 2003 15:41:49 -0000
@@ -26,6 +26,19 @@ static unsigned char MMC_WRITE_10[] = {
static unsigned char MMC_GET_CONFIGURATION[] ={ 0x46, 0, 0, 0, 0, 0, 16, 0, 0 };
static unsigned char MMC_SYNC_CACHE[] = { 0x35, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
static unsigned char MMC_GET_EVENT[] = { 0x4A, 1, 0, 0, 16, 0, 0, 0, 8, 0 };
+static unsigned char MMC_REQUEST_SENSE[] = { 0x03, 0, 0, 0, 18, 0};
+
+void mmc_request_sense(struct drive *d, struct buffer *buf)
+{
+ struct command c;
+ c.oplen = sizeof(MMC_REQUEST_SENSE);
+ memcpy(c.opcode, MMC_REQUEST_SENSE, sizeof(MMC_REQUEST_SENSE));
+ c.page = buf;
+ c.page->sectors = 0;
+ c.page->bytes = 0;
+ c.dir = FROM_DRIVE;
+ d->issue_command(d, &c);
+}
void mmc_get_event(struct drive *d)
{
@@ -302,13 +315,15 @@ printf("%d, %d, %d, %d\n", c.sense[3], c
}
}
-void mmc_erase(struct drive *d, int fast)
+void mmc_erase(struct drive *d, enum libburn_erase_types type)
{
struct command c;
memcpy(c.opcode, MMC_ERASE, sizeof(MMC_ERASE));
-
- c.opcode[1] = !!fast;
+ /* we need IMMED set to 1 to get the progress status */
+ c.opcode[1] = 16;
+ /* erasing type */
+ c.opcode[1] |= type;
c.oplen = sizeof(MMC_ERASE);
c.page = NULL;
c.dir = NO_TRANSFER;
Index: libburn/mmc.h
===================================================================
RCS file: /cvs/burn/burn/libburn/mmc.h,v
retrieving revision 1.32
diff -p -u -r1.32 mmc.h
--- libburn/mmc.h 13 Oct 2003 19:45:03 -0000 1.32
+++ libburn/mmc.h 4 Dec 2003 15:41:49 -0000
@@ -12,11 +12,11 @@ struct buffer;
void mmc_read(struct drive *);
void mmc_get_event(struct drive *);
-void mmc_write(struct drive *, int start, struct buffer *buf);
+void mmc_write(struct drive *, int, struct buffer *);
void mmc_sync_cache(struct drive *);
void mmc_load(struct drive *);
void mmc_eject(struct drive *);
-void mmc_erase(struct drive *, int);
+void mmc_erase(struct drive *, enum libburn_erase_types type);
void mmc_read_toc(struct drive *);
void mmc_read_disc_info(struct drive *);
void mmc_read_atip(struct drive *);
@@ -29,5 +29,6 @@ void mmc_set_speed(struct drive *, int,
void mmc_read_lead_in(struct drive *, struct buffer *);
void mmc_perform_opc(struct drive *);
void mmc_get_configuration(struct drive *);
+void mmc_request_sense(struct drive *, struct buffer *);
#endif /*__MMC*/
Index: libburn/sg.c
===================================================================
RCS file: /cvs/burn/burn/libburn/sg.c,v
retrieving revision 1.106
diff -p -u -r1.106 sg.c
--- libburn/sg.c 2 Dec 2003 00:02:12 -0000 1.106
+++ libburn/sg.c 4 Dec 2003 15:41:51 -0000
@@ -121,6 +121,7 @@ static void enumerate_common(char *fname
out.send_parameters = spc_select_error_params;
out.send_write_parameters = spc_select_write_params;
out.sync_cache = mmc_sync_cache;
+ out.request_sense = mmc_request_sense;
out.idata = malloc(sizeof(struct scsi_inquiry_data));
out.idata->valid = 0;
Index: libburn/transport.h
===================================================================
RCS file: /cvs/burn/burn/libburn/transport.h,v
retrieving revision 1.87
diff -p -u -r1.87 transport.h
--- libburn/transport.h 2 Dec 2003 03:04:17 -0000 1.87
+++ libburn/transport.h 4 Dec 2003 15:41:52 -0000
@@ -114,7 +114,7 @@ unsigned char mediacatalog[13];
int (*issue_command) (struct drive *, struct command *);
/* lower level functions */
- void (*erase) (struct drive *, int);
+ void (*erase) (struct drive *, enum libburn_erase_types);
void (*getcaps) (struct drive *);
void (*write) (struct drive *, int, struct buffer *);
void (*read_toc) (struct drive *);
@@ -135,6 +135,7 @@ unsigned char mediacatalog[13];
void (*send_write_parameters) (struct drive *,
const struct libburn_write_opts *);
void (*sync_cache) (struct drive *);
+ void (*request_sense) (struct drive *, struct buffer *);
struct params params;
struct scsi_inquiry_data *idata;
struct scsi_mode_data *mdata;
Index: test/blank.c
===================================================================
RCS file: /cvs/burn/burn/test/blank.c,v
retrieving revision 1.11
diff -p -u -r1.11 blank.c
--- test/blank.c 25 Oct 2003 03:38:23 -0000 1.11
+++ test/blank.c 4 Dec 2003 15:41:52 -0000
@@ -15,6 +15,7 @@ static unsigned int n_drives;
static void blank_disc(struct drive *drive)
{
enum libburn_drive_status s;
+ struct libburn_progress progress;
if (libburn_drive_grab(drive, 1) != LIBBURN_GRAB_OK) {
fprintf(stderr, "Unable to open the drive!\n");
@@ -33,11 +34,14 @@ static void blank_disc(struct drive *dri
return;
}
- fprintf(stderr, "Blanking disc...");
- libburn_erase_disc(drive, 1);
-
- while (libburn_drive_get_busy(drive, NULL))
- usleep(1000);
+ fprintf(stderr, "Blanking disc...\n");
+ libburn_erase_disc(drive, LIBBURN_ERASE_MINIMAL);
+ fprintf(stderr, "please wait...\n");
+
+ while (libburn_drive_get_busy(drive, &progress)) {
+ fprintf(stderr, "%d\n", progress.abs_sector);
+ usleep(500);
+ }
fprintf(stderr, "Done\n");
libburn_drive_release(drive, 0);
Index: test/burniso.c
===================================================================
RCS file: /cvs/burn/burn/test/burniso.c,v
retrieving revision 1.35
diff -p -u -r1.35 burniso.c
--- test/burniso.c 2 Dec 2003 02:25:22 -0000 1.35
+++ test/burniso.c 4 Dec 2003 15:41:52 -0000
@@ -54,10 +54,10 @@ void burn_iso(struct drive *drive, const
return;
}
o = libburn_write_opts_new();
- o->perform_opc = 1;
+ o->perform_opc = 0;
o->write_type = LIBBURN_WRITE_RAW;
o->block_type = LIBBURN_BLOCK_RAW16;
- o->simulate = 1;
+ o->simulate = 0;
o->underrun_proof = 0;
libburn_structure_print_disc(disc);
@@ -65,7 +65,7 @@ void burn_iso(struct drive *drive, const
libburn_write_opts_free(o);
while (libburn_drive_get_busy(drive, NULL)) {
- sleep(1);
+ sleep(100);
}
printf("\n");
libburn_drive_release(drive, 0);
--=-pIRI6xUk7jKcwMEBXSSK--