Implemented DVD-R[W] DAO as BURN_WRITE_SAO
This commit is contained in:
parent
073ff204b3
commit
3f35513991
@ -1 +1 @@
|
||||
#define Cdrskin_timestamP "2007.02.05.132335"
|
||||
#define Cdrskin_timestamP "2007.02.06.130410"
|
||||
|
@ -1590,6 +1590,8 @@ int burn_disc_get_multi_caps(struct burn_drive *d, enum burn_write_types wt,
|
||||
} else if (s == BURN_DISC_APPENDABLE &&
|
||||
(wt == BURN_WRITE_SAO || wt == BURN_WRITE_RAW)) {
|
||||
return 0;
|
||||
} else if (wt == BURN_WRITE_RAW && !d->current_is_cd_profile) {
|
||||
return 0;
|
||||
} else if (d->current_profile == 0x09 || d->current_profile == 0x0a) {
|
||||
/* CD-R , CD-RW */
|
||||
if (d->block_types[BURN_WRITE_TAO]) {
|
||||
@ -1609,13 +1611,21 @@ int burn_disc_get_multi_caps(struct burn_drive *d, enum burn_write_types wt,
|
||||
if (o->advised_write_mode == BURN_WRITE_NONE)
|
||||
o->advised_write_mode = BURN_WRITE_RAW;
|
||||
}
|
||||
if (wt == BURN_WRITE_RAW)
|
||||
o->multi_session = o->multi_track = 0;
|
||||
} else if (d->current_profile == 0x11 || d->current_profile == 0x14) {
|
||||
/* DVD-R , sequential DVD-RW */
|
||||
if (s == BURN_DISC_BLANK) {
|
||||
o->might_do_sao = 1;
|
||||
o->advised_write_mode = BURN_WRITE_SAO;
|
||||
}
|
||||
if (d->current_has_feat21h) {
|
||||
o->multi_session = o->multi_track = 1;
|
||||
o->might_do_tao = 2;
|
||||
o->advised_write_mode = BURN_WRITE_TAO;
|
||||
}
|
||||
if (wt == BURN_WRITE_SAO)
|
||||
o->multi_session = o->multi_track = 0;
|
||||
} else if (d->current_profile == 0x12 || d->current_profile == 0x13 ||
|
||||
d->current_profile == 0x1a) {
|
||||
/* DVD-RAM, overwriteable DVD-RW, DVD+RW */
|
||||
|
@ -107,24 +107,31 @@ struct burn_write_opts;
|
||||
enum burn_write_types
|
||||
{
|
||||
/** Packet writing.
|
||||
currently unsupported
|
||||
currently unsupported, (for DVD Incremental Streaming use TAO)
|
||||
*/
|
||||
BURN_WRITE_PACKET,
|
||||
|
||||
/** Track At Once recording.
|
||||
2s gaps between tracks, no fonky lead-ins
|
||||
/** With CD: Track At Once recording
|
||||
2s gaps between tracks, no fonky lead-ins
|
||||
|
||||
With sequential DVD-R[W]: Incremental Streaming
|
||||
With DVD-RAM/+RW: Random Writeable (used sequentially)
|
||||
With overwriteable DVD-RW: Rigid Restricted Overwrite
|
||||
*/
|
||||
BURN_WRITE_TAO,
|
||||
|
||||
/** Session At Once.
|
||||
Block type MUST be BURN_BLOCK_SAO
|
||||
ts A70122 : Currently not capable of mixing data and audio tracks.
|
||||
/** With CD: Session At Once
|
||||
Block type MUST be BURN_BLOCK_SAO
|
||||
ts A70122: Currently not capable of mixing data and audio tracks.
|
||||
|
||||
With sequential DVD-R[W]: Disc-at-once, DAO
|
||||
Single session, single track, fixed size mandatory, (-dvd-compat)
|
||||
*/
|
||||
BURN_WRITE_SAO,
|
||||
|
||||
/** Raw disc at once recording.
|
||||
all subcodes must be provided by lib or user
|
||||
only raw block types are supported
|
||||
/** With CD: Raw disc at once recording.
|
||||
all subcodes must be provided by lib or user
|
||||
only raw block types are supported
|
||||
*/
|
||||
BURN_WRITE_RAW,
|
||||
|
||||
@ -1385,6 +1392,10 @@ struct burn_multi_caps {
|
||||
writing a session. It also guarantees that the drive will be able
|
||||
to predict and use the appropriate Next Writeable Address to place
|
||||
the next session on the media without overwriting the existing ones.
|
||||
It does not guarantee that the selected write type is able to do
|
||||
an appending session after the next session. (E.g. CD SAO is capable
|
||||
of multi-session by keeping a disc appendable. But .might_do_sao
|
||||
will be 0 afterwards, when checking the appendable media.)
|
||||
1= media may be kept appendable by burn_write_opts_set_multi(o,1)
|
||||
0= media will not be apendable appendable
|
||||
*/
|
||||
@ -1447,7 +1458,7 @@ struct burn_multi_caps {
|
||||
via burn_disc_free_multi_caps() when no longer needed.
|
||||
@param d The drive to inquire
|
||||
@param wt With BURN_WRITE_NONE the best capabilities of all write modes
|
||||
get returned. If set to a write mode like BURN_WRITE_TAO the
|
||||
get returned. If set to a write mode like BURN_WRITE_SAO the
|
||||
capabilities with that particular mode are returned.
|
||||
@param caps returns the info structure
|
||||
@param flag Bitfield for control purposes (unused yet, submit 0)
|
||||
|
@ -352,6 +352,12 @@ Range "scdbackup" : 0x00020000 to 0x0002ffff
|
||||
0x00020131 (SORRY,HIGH) = No suitable formatting type offered by drive
|
||||
0x00020132 (SORRY,HIGH) = Selected format is not suitable for libburn
|
||||
0x00020133 (SORRY,HIGH) = Cannot mix data and audio in SAO mode
|
||||
0x00020134 (NOTE,HIGH) = Defaulted TAO to DAO
|
||||
0x00020135 (SORRY,HIGH) = Cannot perform TAO, job unsuitable for DAO
|
||||
0x00020136 (SORRY,HIGH) = DAO Burning restricted to single fixed size track
|
||||
0x00020137 (HINT,HIGH) = TAO would be possible
|
||||
0x00020138 (FATAL,HIGH) = Cannot reserve track
|
||||
|
||||
|
||||
libdax_audioxtr:
|
||||
0x00020200 (SORRY,HIGH) = Cannot open audio source file
|
||||
|
@ -208,20 +208,27 @@ int mmc_reserve_track(struct burn_drive *d, off_t size)
|
||||
{
|
||||
struct command c;
|
||||
int lba;
|
||||
char msg[80];
|
||||
|
||||
mmc_function_spy("mmc_reserve_track");
|
||||
c.retry = 1;
|
||||
c.oplen = sizeof(MMC_RESERVE_TRACK);
|
||||
memcpy(c.opcode, MMC_RESERVE_TRACK, sizeof(MMC_RESERVE_TRACK));
|
||||
|
||||
/* Nice rounding trick learned from dvd+rw-tools */
|
||||
/* Round to 32 KiB and divide by 2048
|
||||
(by nice binary rounding trick learned from dvd+rw-tools) */
|
||||
lba = ((size + (off_t) 0x7fff) >> 11) & ~0xf;
|
||||
mmc_int_to_four_char(c.opcode+5, lba);
|
||||
|
||||
sprintf(msg, "reserving track of %d blocks", lba);
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x00000002,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_ZERO,
|
||||
msg, 0, 0);
|
||||
|
||||
c.page = NULL;
|
||||
c.dir = NO_TRANSFER;
|
||||
d->issue_command(d, &c);
|
||||
return !!c.error;
|
||||
return !c.error;
|
||||
}
|
||||
|
||||
|
||||
@ -1521,6 +1528,10 @@ void mmc_get_configuration(struct burn_drive *d)
|
||||
if (cp == 0x12)
|
||||
d->current_is_supported_profile = 1;
|
||||
#endif
|
||||
#ifdef Libburn_support_dvd_r_seQ
|
||||
if (cp == 0x11 || cp == 0x14)
|
||||
d->current_is_supported_profile = 1;
|
||||
#endif
|
||||
|
||||
/* Enable this to get loud and repeated reports about the feature set :
|
||||
#define Libburn_print_feature_descriptorS 1
|
||||
@ -1645,11 +1656,6 @@ void mmc_get_configuration(struct burn_drive *d)
|
||||
|
||||
}
|
||||
}
|
||||
#ifdef Libburn_support_dvd_r_seQ
|
||||
/* might get adjusted later by mmc_read_disc_info() */
|
||||
if ((cp == 0x11 || cp == 0x14) && d->current_has_feat21h)
|
||||
d->current_is_supported_profile = 1;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
@ -1778,6 +1784,11 @@ void mmc_sync_cache(struct burn_drive *d)
|
||||
c.oplen = sizeof(MMC_SYNC_CACHE);
|
||||
c.page = NULL;
|
||||
c.dir = NO_TRANSFER;
|
||||
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x00000002,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_ZERO,
|
||||
"\nsyncing cache", 0, 0);
|
||||
|
||||
d->issue_command(d, &c);
|
||||
}
|
||||
|
||||
@ -2232,8 +2243,8 @@ int mmc_compose_mode_page_5(struct burn_drive *d,
|
||||
pd[0] = 5;
|
||||
pd[1] = d->mdata->write_page_length;
|
||||
|
||||
/* ts A61229 */
|
||||
if (d->current_profile == 0x13) { /* DVD-RW restricted overwrite */
|
||||
if (d->current_profile == 0x13) {
|
||||
/* A61229 : DVD-RW restricted overwrite */
|
||||
/* learned from transport.hxx : page05_setup()
|
||||
and mmc3r10g.pdf table 347 */
|
||||
/* BUFE (burnproof), no LS_V (i.e. default Link Size, i hope),
|
||||
@ -2247,11 +2258,28 @@ int mmc_compose_mode_page_5(struct burn_drive *d,
|
||||
pd[5] = 0;
|
||||
|
||||
} else if ((d->current_profile == 0x14 || d->current_profile == 0x11)
|
||||
&& d->current_has_feat21h == 1) { /* ts A70128 */
|
||||
/* learned from transport.hxx : page05_setup()
|
||||
&& o->write_type == BURN_WRITE_SAO) {
|
||||
/* ts A70205 : DVD-R[W} : Disc-at-once, DAO */
|
||||
/* Learned from dvd+rw-tools and mmc5r03c.pdf .
|
||||
See doc/cookbook.txt for more detailed references. */
|
||||
|
||||
/* BUFE , LS_V = 0, Test Write, Write Type = 2 SAO (DAO) */
|
||||
pd[2] = ((!!o->underrun_proof) << 6)
|
||||
| ((!!o->simulate) << 4)
|
||||
| 2;
|
||||
/* No multi-session , FP = 0 , Track Mode = 5 */
|
||||
pd[3] = 5;
|
||||
/* Data Block Type = 8 */
|
||||
pd[4] = 8;
|
||||
|
||||
} else if (d->current_profile == 0x14 || d->current_profile == 0x11) {
|
||||
/* ts A70128 : DVD-R[W] Incremental Streaming */
|
||||
/* Learned from transport.hxx : page05_setup()
|
||||
and mmc5r03c.pdf 7.5, 4.2.3.4 Table 17
|
||||
and spc3r23.pdf 6.8, 7.4.3 */
|
||||
/* BUFE , LS_V = 1, Test Write, Write Type = 00h Incremental */
|
||||
|
||||
/* BUFE , LS_V = 1, Test Write,
|
||||
Write Type = 0 Packet/Incremental */
|
||||
pd[2] = ((!!o->underrun_proof) << 6)
|
||||
| (1 << 5)
|
||||
| ((!!o->simulate) << 4);
|
||||
@ -2279,6 +2307,7 @@ int mmc_compose_mode_page_5(struct burn_drive *d,
|
||||
|
||||
} else {
|
||||
/* Traditional setup for CD */
|
||||
|
||||
pd[2] = ((!!o->underrun_proof) << 6)
|
||||
| ((!!o->simulate) << 4)
|
||||
| (o->write_type & 0x0f);
|
||||
|
@ -869,22 +869,40 @@ int burn_disc_init_write_status(struct burn_write_opts *o,
|
||||
|
||||
|
||||
/* ts A70129 : learned much from dvd+rw-tools-7.0/growisofs_mmc.cpp */
|
||||
int burn_disc_open_track_dvd_minus_r(struct burn_write_opts *o, int tnum)
|
||||
int burn_disc_open_track_dvd_minus_r(struct burn_write_opts *o,
|
||||
struct burn_session *s, int tnum)
|
||||
{
|
||||
struct burn_drive *d = o->drive;
|
||||
char msg[160];
|
||||
int ret, lba, nwa;
|
||||
off_t size;
|
||||
|
||||
d->send_write_parameters(d, o);
|
||||
ret = d->get_nwa(d, -1, &lba, &nwa);
|
||||
sprintf(msg,
|
||||
"DVD pre-track %2.2d : get_nwa(%d), ret= %d , d->nwa= %d\n",
|
||||
tnum+1, nwa, ret, d->nwa);
|
||||
libdax_msgs_submit(libdax_messenger, d->global_index, 0x000002,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_ZERO,
|
||||
msg,0,0);
|
||||
libdax_msgs_submit(libdax_messenger, d->global_index, 0x000002,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_ZERO, msg,0,0);
|
||||
if (nwa > d->nwa)
|
||||
d->nwa = nwa;
|
||||
|
||||
if (o->write_type == BURN_WRITE_SAO) { /* DAO */
|
||||
/* Round track size up to 32 KiB and reserve track */
|
||||
size = ((off_t) burn_track_get_sectors(s->track[tnum]))
|
||||
* (off_t) 2048;
|
||||
size = (size + (off_t) 0x7fff) & ~((off_t) 0x7fff);
|
||||
ret = d->reserve_track(d, size);
|
||||
if (ret <= 0) {
|
||||
sprintf(msg, "Cannot reserve track of %.f bytes",
|
||||
(double) size);
|
||||
libdax_msgs_submit(libdax_messenger, d->global_index,
|
||||
0x00020138,
|
||||
LIBDAX_MSGS_SEV_FATAL, LIBDAX_MSGS_PRIO_HIGH,
|
||||
msg, 0,0);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -896,8 +914,8 @@ int burn_disc_close_track_dvd_minus_r(struct burn_write_opts *o,
|
||||
struct burn_drive *d = o->drive;
|
||||
char msg[80];
|
||||
|
||||
/* only DVD-R or sequential DVD-RW */
|
||||
if (d->current_has_feat21h != 1) /* only with Incremental writing */
|
||||
/* only with Incremental writing */
|
||||
if (o->write_type != BURN_WRITE_TAO)
|
||||
return 2;
|
||||
|
||||
sprintf(msg, "Closing track %2.2d (absolute track number %d)",
|
||||
@ -929,7 +947,7 @@ int burn_dvd_write_track(struct burn_write_opts *o,
|
||||
|
||||
if (d->current_profile == 0x11 || d->current_profile == 0x14) {
|
||||
/* DVD-R, DVD-RW Sequential */
|
||||
ret = burn_disc_open_track_dvd_minus_r(o, tnum);
|
||||
ret = burn_disc_open_track_dvd_minus_r(o, s, tnum);
|
||||
if (ret <= 0)
|
||||
goto ex;
|
||||
}
|
||||
@ -1026,8 +1044,9 @@ int burn_disc_close_session_dvd_minus_r(struct burn_write_opts *o,
|
||||
{
|
||||
struct burn_drive *d = o->drive;
|
||||
|
||||
if (d->current_has_feat21h != 1)
|
||||
return 2; /* only for Incremental writing */
|
||||
/* only for Incremental writing */
|
||||
if (o->write_type != BURN_WRITE_TAO)
|
||||
return 2;
|
||||
|
||||
libdax_msgs_submit(libdax_messenger, o->drive->global_index,0x00020119,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_HIGH,
|
||||
@ -1047,7 +1066,7 @@ int burn_dvd_write_session(struct burn_write_opts *o,
|
||||
int i,ret;
|
||||
struct burn_drive *d = o->drive;
|
||||
|
||||
/* >>> open_session ? (maybe with DAO) */
|
||||
/* >>> open_session ? */
|
||||
|
||||
for (i = 0; i < s->tracks; i++) {
|
||||
ret = burn_dvd_write_track(o, s, i);
|
||||
@ -1189,11 +1208,7 @@ int burn_disc_setup_dvd_minus_r(struct burn_write_opts *o,
|
||||
{
|
||||
struct burn_drive *d = o->drive;
|
||||
|
||||
if (d->current_has_feat21h) {
|
||||
/* most setup is in burn_disc_setup_track_dvd_minus_r() */;
|
||||
} else {
|
||||
return 0; /* >>> no DAO for now */
|
||||
}
|
||||
/* most setup is in burn_disc_setup_track_dvd_minus_r() */;
|
||||
|
||||
d->nwa = 0;
|
||||
return 1;
|
||||
@ -1204,7 +1219,7 @@ int burn_disc_setup_dvd_minus_r(struct burn_write_opts *o,
|
||||
int burn_dvd_write_sync(struct burn_write_opts *o,
|
||||
struct burn_disc *disc)
|
||||
{
|
||||
int i, ret, sx, tx, mode, exotic_track = 0;
|
||||
int i, ret, sx, tx, mode, exotic_track = 0, dao_is_ok;
|
||||
struct burn_drive *d = o->drive;
|
||||
char msg[160];
|
||||
|
||||
@ -1289,9 +1304,47 @@ int burn_dvd_write_sync(struct burn_write_opts *o,
|
||||
/* _Rigid_ Restricted Overwrite demands this */
|
||||
o->obs_pad = 1; /* fill-up track's last 32k buffer */
|
||||
|
||||
} else if ((d->current_profile == 0x11 || d->current_profile == 0x14)
|
||||
&& d->current_has_feat21h == 1) {
|
||||
/* DVD-R , DVD-RW Sequential (for now only Incremental) */
|
||||
} else if (d->current_profile == 0x11 || d->current_profile == 0x14) {
|
||||
/* DVD-R , DVD-RW Sequential */
|
||||
dao_is_ok =
|
||||
(disc->sessions == 1 &&
|
||||
disc->session[0]->tracks == 1 &&
|
||||
(! burn_track_is_open_ended(
|
||||
disc->session[0]->track[0])) &&
|
||||
(!o->multi) && d->status == BURN_DISC_BLANK
|
||||
);
|
||||
if (o->write_type == BURN_WRITE_TAO &&
|
||||
!d->current_has_feat21h) {
|
||||
if (dao_is_ok) {
|
||||
o->write_type = BURN_WRITE_SAO;
|
||||
libdax_msgs_submit(libdax_messenger,
|
||||
d->global_index, 0x00020134,
|
||||
LIBDAX_MSGS_SEV_NOTE, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"Defaulted TAO to DAO (lack of feature 21h)",
|
||||
0, 0);
|
||||
} else {
|
||||
libdax_msgs_submit(libdax_messenger,
|
||||
d->global_index, 0x00020135,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"Cannot perform TAO (lack of feature 21h), job unsuitable for DAO",
|
||||
0, 0);
|
||||
goto early_failure;
|
||||
}
|
||||
} else if (o->write_type == BURN_WRITE_SAO && !dao_is_ok) {
|
||||
libdax_msgs_submit(libdax_messenger, d->global_index,
|
||||
0x00020136,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"DAO burning is restricted to a single fixed size track and no multi-session",
|
||||
0,0);
|
||||
if (d->current_has_feat21h)
|
||||
libdax_msgs_submit(libdax_messenger,
|
||||
d->global_index, 0x00020137,
|
||||
LIBDAX_MSGS_SEV_HINT,
|
||||
LIBDAX_MSGS_PRIO_HIGH,
|
||||
"TAO would be possible and could do the job",
|
||||
0,0);
|
||||
goto early_failure;
|
||||
}
|
||||
if (o->start_byte >= 0) {
|
||||
sprintf(msg, "Write start address not supported");
|
||||
libdax_msgs_submit(libdax_messenger, d->global_index,
|
||||
|
Loading…
Reference in New Issue
Block a user