Compare commits
41 Commits
ZeroFourEi
...
ZeroFiveFo
Author | SHA1 | Date | |
---|---|---|---|
757be624b9 | |||
7b5512f84c | |||
40e760532a | |||
129b80cca9 | |||
935239b4f9 | |||
e50cc04374 | |||
89c12404d0 | |||
78642d08ae | |||
c2c2499862 | |||
32252122b8 | |||
63a48571af | |||
006fb98aee | |||
afded80e10 | |||
fb3d2de5df | |||
c640c7954b | |||
bc30c4201a | |||
50b587a22c | |||
cd99716ab5 | |||
13bdbd3555 | |||
711c055730 | |||
f64ed23a98 | |||
730c1555ab | |||
acd7dbc5c6 | |||
6dc9ecbcad | |||
5a99f9c4d8 | |||
ea17318e18 | |||
98d742a4ef | |||
332a92ac78 | |||
6c50416d3c | |||
91d678a503 | |||
76e85e600c | |||
9d48bb6892 | |||
38f0399fff | |||
39198ff8cb | |||
67ca4a251a | |||
b1c6953b61 | |||
eb95d89272 | |||
548051e53f | |||
a72b38c116 | |||
a67aa2ccee | |||
2fb5ea8def |
@ -101,9 +101,9 @@ test_structest_CPPFLAGS = -Ilibburn
|
||||
test_structest_LDADD = $(libburn_libburn_la_OBJECTS) $(THREAD_LIBS)
|
||||
test_structest_SOURCES = test/structest.c
|
||||
|
||||
## cdrskin construction site - ts A60816 - A80517
|
||||
## cdrskin construction site - ts A60816 - A80820
|
||||
cdrskin_cdrskin_CPPFLAGS = -Ilibburn
|
||||
cdrskin_cdrskin_CFLAGS = -DCdrskin_libburn_0_4_8
|
||||
cdrskin_cdrskin_CFLAGS = -DCdrskin_libburn_0_5_4
|
||||
|
||||
# cdrskin_cdrskin_LDADD = $(libburn_libburn_la_OBJECTS) $(THREAD_LIBS)
|
||||
# ts A80123, change proposed by Simon Huggins to cause dynamic libburn linking
|
||||
|
41
README
41
README
@ -12,12 +12,6 @@ Still containing parts of
|
||||
Libburn. By Derek Foreman <derek@signalmarketing.com> and
|
||||
Ben Jansens <xor@orodu.net>
|
||||
Copyright (C) 2002-2006 Derek Foreman and Ben Jansens
|
||||
These parts are to be replaced by own code of above libburnia-project.org
|
||||
copyright holders and then libburnia-project.org is to be their sole copyright.
|
||||
This is done to achieve the right to issue the clarification and the
|
||||
commitment as written at the end of this text.
|
||||
The rights and merits of the Libburn-copyright holders Derek Foreman and
|
||||
Ben Jansens will be duely respected.
|
||||
|
||||
This libburnia-project.org toplevel README (C) 2006-2008 Thomas Schmitt
|
||||
------------------------------------------------------------------------------
|
||||
@ -173,7 +167,7 @@ Project history as far as known to me:
|
||||
discontent.
|
||||
The situation first caused me to publically regret it and then - after i
|
||||
got the opportunity to move in with cdrskin - gave me true reason to
|
||||
personally apologize to Derek Foreman, Ben Jansens and the contibutors at
|
||||
personally apologize to Derek Foreman, Ben Jansens and the contributors at
|
||||
icculus.org/burn. Posted to both projects:
|
||||
http://lists.freedesktop.org/archives/libburn/2006-August/000446.html
|
||||
http://mailman-mail1.webfaction.com/pipermail/libburn-hackers/2006-August/000024.html
|
||||
@ -277,7 +271,7 @@ Project history as far as known to me:
|
||||
image tree nodes. It now depends on libisofs-0.6.4 and libburn-0.4.4.
|
||||
xorriso makes use of new libisofs features by performing incremental
|
||||
updates of directory trees and by cutting oversized data files into
|
||||
pieces. A primitive single session emulation of cdrcord and mkisofs is
|
||||
pieces. A primitive single session emulation of cdrecord and mkisofs is
|
||||
provided.
|
||||
|
||||
- 10th May 2008 libburn-0.4.6 supports formatting and writing of BD-RE,
|
||||
@ -287,6 +281,37 @@ Project history as far as known to me:
|
||||
- 17th May 2008 an old bug with DVD-RAM and now with BD-RE is fixed by
|
||||
libburn-0.4.8 to allow libisoburn emulation of multisession on those media.
|
||||
|
||||
- 19th May 2008 libisoburn-0.1.6 brings better table-of-content emulation
|
||||
on overwriteble media and disk files.
|
||||
|
||||
- 1st Jun 2008 libisofs-0.6.6 fixes some problems around device files.
|
||||
|
||||
- 3rd Jun 2008 libisoburn-0.1.8 fixes a bug with overwriteable media.
|
||||
|
||||
- 23rd Jun 2008 libisoburn-0.2.0 introduces extraction of files from
|
||||
ISO images.
|
||||
|
||||
- 16th Jul 2008 libburn-0.5.0 handles systems with no /dev/sr* but only
|
||||
/dev/scd*.
|
||||
|
||||
- 19th Jul 2008 libisoburn/xorriso-0.2.2 can do multi-session in mkisofs
|
||||
and cdrecord style. xorriso now can serve underneath growisofs.
|
||||
|
||||
- 20th Aug 2008 libburn-0.5.2 revokes the necessity that a drive must be
|
||||
enumerable in order to be adressable. Enumeration is enhanced by examining
|
||||
/proc/sys/dev/cdrom/info.
|
||||
|
||||
- 24th Aug 2008 libisoburn/xorriso-0.2.4 introduces a media readability check
|
||||
with data retrieval option.
|
||||
|
||||
- 18th Sep 2008 libisofs-0.6.8 supports ISO 9660 Level 3 which allows very
|
||||
large data files in the image.
|
||||
|
||||
- 20th Sep 2008 libisoburn/xorriso-0.2.6 takes into respect the new Level 3
|
||||
capabilities of libisofs.
|
||||
|
||||
- 6th Oct 2008 libburn-0.5.4 adjusts the changes of 0.5.2 to the needs of
|
||||
Linux kernel 2.4 and introduces human readable SCSI error messages.
|
||||
|
||||
|
||||
------------------------------------------------------------------------------
|
||||
|
@ -4,7 +4,7 @@
|
||||
cdrskin. By Thomas Schmitt <scdbackup@gmx.net>
|
||||
Integrated sub project of libburnia-project.org but also published via:
|
||||
http://scdbackup.sourceforge.net/cdrskin_eng.html
|
||||
http://scdbackup.sourceforge.net/cdrskin-0.4.8.pl00.tar.gz
|
||||
http://scdbackup.sourceforge.net/cdrskin-0.5.4.pl00.tar.gz
|
||||
Copyright (C) 2006-2008 Thomas Schmitt, provided under GPL version 2.
|
||||
------------------------------------------------------------------------------
|
||||
|
||||
@ -20,10 +20,10 @@ By using this software you agree to the disclaimer at the end of this text
|
||||
|
||||
Compilation, First Glimpse, Installation
|
||||
|
||||
Obtain cdrskin-0.4.8.pl00.tar.gz, take it to a directory of your choice and do:
|
||||
Obtain cdrskin-0.5.4.pl00.tar.gz, take it to a directory of your choice and do:
|
||||
|
||||
tar xzf cdrskin-0.4.8.pl00.tar.gz
|
||||
cd cdrskin-0.4.8
|
||||
tar xzf cdrskin-0.5.4.pl00.tar.gz
|
||||
cd cdrskin-0.5.4
|
||||
|
||||
Within that directory execute:
|
||||
|
||||
|
@ -38,7 +38,7 @@ original="./libburn_svn_release.tgz"
|
||||
# My changes are in $changes , mainly in $changes/cdrskin
|
||||
changes="./libburn-release"
|
||||
|
||||
skin_release="0.4.8"
|
||||
skin_release="0.5.4"
|
||||
patch_level=".pl00"
|
||||
skin_rev="$skin_release""$patch_level"
|
||||
|
@ -38,7 +38,7 @@ original="./libburn_svn.tgz"
|
||||
# My changes are in $changes , mainly in $changes/cdrskin
|
||||
changes="./libburn-develop"
|
||||
|
||||
skin_release="0.4.9"
|
||||
skin_release="0.5.5"
|
||||
patch_level=""
|
||||
skin_rev="$skin_release""$patch_level"
|
||||
|
||||
@ -239,7 +239,7 @@ rm -rf "$target"
|
||||
./"$bintarget_dynamic" -version
|
||||
./"$bintarget_static" -version
|
||||
ls -l "$cdrskin_tarball"
|
||||
ls -l "$bintarget_dynamic"*
|
||||
ls -l "$bintarget_dynamic"
|
||||
ls -l "$bintarget_static"
|
||||
ls -l $(basename "$man_page_html")
|
||||
|
@ -2,7 +2,7 @@
|
||||
.\" First parameter, NAME, should be all caps
|
||||
.\" Second parameter, SECTION, should be 1-8, maybe w/ subsection
|
||||
.\" other parameters are allowed: see man(7), man(1)
|
||||
.TH CDRSKIN 1 "May 17, 2008"
|
||||
.TH CDRSKIN 1 "Aug 05, 2008"
|
||||
.\" Please adjust this date whenever revising the manpage.
|
||||
.\"
|
||||
.\" Some roff macros, for reference:
|
||||
@ -108,8 +108,9 @@ While audio tracks just contain a given time span of acoustic vibrations,
|
||||
data tracks may have an arbitray meaning. Nevertheless, ISO-9660 filesystems
|
||||
are established as a format which can represent a tree of directories and
|
||||
files on all major operating systems. Such filesystem images can be
|
||||
produced by programs mkisofs or genisoimage. They can also be extended by
|
||||
follow-up tracks if prepared properly. See the man pages of said programs.
|
||||
produced by programs mkisofs or genisoimage or xorriso.
|
||||
They can also be extended by follow-up tracks if prepared properly.
|
||||
See the man pages of said programs.
|
||||
cdrskin is able to fulfill the needs about their option -C.
|
||||
.br
|
||||
Another type of data track content are archive formats which originally
|
||||
@ -617,7 +618,8 @@ Note: msifile=path is actually an option of wodim and not of cdrecord.
|
||||
.TP
|
||||
.BI \-msinfo
|
||||
Retrieve multi-session info for preparing a follow-up session by option -C
|
||||
of programs mkisofs or genisoimage. Print result to standard output.
|
||||
of programs mkisofs, genisoimage, or xorriso -as mkisofs.
|
||||
Print result to standard output.
|
||||
This option redirects to stderr all message output except the one of option
|
||||
--tell_media_space and its own result string, which consists of two numbers.
|
||||
The result string shall be used as argument of option -C with said programs.
|
||||
@ -1080,8 +1082,9 @@ Linux specific: Do not ask the operating system to prevent opening busy drives.
|
||||
Wether this leads to senseful behavior depends on operating system and kernel.
|
||||
.TP
|
||||
.BI drive_scsi_dev_family= sr | scd | sg
|
||||
Linux specific: Select a SCSI device file family to be used for drive command
|
||||
transactions. Normally this is /dev/sgN on kernel versions < 2.6 and /dev/srN
|
||||
Linux specific: Select a SCSI device file family to be scanned for by
|
||||
options --devices and -scanbus.
|
||||
Normally this is /dev/sgN on kernel versions < 2.6 and /dev/srN
|
||||
on kernels >= 2.6 . This option allows to explicitely override that default
|
||||
in order to meet other programs at a common device file for each drive.
|
||||
On kernel 2.4 families sr and scd will find no drives.
|
||||
|
@ -88,7 +88,7 @@ or
|
||||
|
||||
/** The official program version */
|
||||
#ifndef Cdrskin_prog_versioN
|
||||
#define Cdrskin_prog_versioN "0.4.8"
|
||||
#define Cdrskin_prog_versioN "0.5.4"
|
||||
#endif
|
||||
|
||||
/** The official libburn interface revision to use.
|
||||
@ -98,10 +98,10 @@ or
|
||||
#define Cdrskin_libburn_majoR 0
|
||||
#endif
|
||||
#ifndef Cdrskin_libburn_minoR
|
||||
#define Cdrskin_libburn_minoR 4
|
||||
#define Cdrskin_libburn_minoR 5
|
||||
#endif
|
||||
#ifndef Cdrskin_libburn_micrO
|
||||
#define Cdrskin_libburn_micrO 8
|
||||
#define Cdrskin_libburn_micrO 4
|
||||
#endif
|
||||
|
||||
|
||||
@ -135,44 +135,44 @@ or
|
||||
#endif /* Cdrskin_libburn_cvs_A60220_tS */
|
||||
|
||||
|
||||
#ifdef Cdrskin_libburn_0_4_8
|
||||
#define Cdrskin_libburn_versioN "0.4.8"
|
||||
#ifdef Cdrskin_libburn_0_5_4
|
||||
#define Cdrskin_libburn_versioN "0.5.4"
|
||||
#define Cdrskin_libburn_from_pykix_svN 1
|
||||
#endif /* Cdrskin_libburn_0_4_8 */
|
||||
#endif /* Cdrskin_libburn_0_5_4 */
|
||||
|
||||
#ifdef Cdrskin_libburn_0_4_9
|
||||
#define Cdrskin_libburn_versioN "0.4.9"
|
||||
#ifdef Cdrskin_libburn_0_5_5
|
||||
#define Cdrskin_libburn_versioN "0.5.5"
|
||||
#define Cdrskin_libburn_from_pykix_svN 1
|
||||
|
||||
/* Place novelty switch macros here.
|
||||
Move them down to Cdrskin_libburn_from_pykix_svN on version leap
|
||||
*/
|
||||
|
||||
/* there are no libburn novelties in 0.4.9 yet */
|
||||
/* there are no libburn novelties in 0.5.5 yet */
|
||||
|
||||
#endif /* Cdrskin_libburn_0_4_9 */
|
||||
#endif /* Cdrskin_libburn_0_5_5 */
|
||||
|
||||
#ifndef Cdrskin_libburn_versioN
|
||||
#define Cdrskin_libburn_0_4_8
|
||||
#define Cdrskin_libburn_versioN "0.4.8"
|
||||
#define Cdrskin_libburn_0_5_4
|
||||
#define Cdrskin_libburn_versioN "0.5.4"
|
||||
#define Cdrskin_libburn_from_pykix_svN 1
|
||||
#endif
|
||||
|
||||
#ifdef Cdrskin_libburn_0_4_8
|
||||
#ifdef Cdrskin_libburn_0_5_4
|
||||
#undef Cdrskin_libburn_majoR
|
||||
#undef Cdrskin_libburn_minoR
|
||||
#undef Cdrskin_libburn_micrO
|
||||
#define Cdrskin_libburn_majoR 0
|
||||
#define Cdrskin_libburn_minoR 4
|
||||
#define Cdrskin_libburn_micrO 6
|
||||
#define Cdrskin_libburn_minoR 5
|
||||
#define Cdrskin_libburn_micrO 4
|
||||
#endif
|
||||
#ifdef Cdrskin_libburn_0_4_9
|
||||
#ifdef Cdrskin_libburn_0_5_5
|
||||
#undef Cdrskin_libburn_majoR
|
||||
#undef Cdrskin_libburn_minoR
|
||||
#undef Cdrskin_libburn_micrO
|
||||
#define Cdrskin_libburn_majoR 0
|
||||
#define Cdrskin_libburn_minoR 4
|
||||
#define Cdrskin_libburn_micrO 7
|
||||
#define Cdrskin_libburn_minoR 5
|
||||
#define Cdrskin_libburn_micrO 5
|
||||
#endif
|
||||
|
||||
|
||||
@ -251,6 +251,10 @@ or
|
||||
/* 0.4.8 */
|
||||
/* Bug fix release for write_start_address=... on DVD-RAM and BD-RE */
|
||||
|
||||
/* 0.5.0 , 0.5.2 , 0.5.4 */
|
||||
/* novel libburn features are transparent to cdrskin */
|
||||
|
||||
|
||||
#ifdef Cdrskin_new_api_tesT
|
||||
|
||||
/* put macros under test caveat here */
|
||||
@ -5504,7 +5508,7 @@ thank_you_for_patience:;
|
||||
if(skin->is_writing)
|
||||
fprintf(stderr,"\n");
|
||||
fprintf(stderr,
|
||||
"\rcdrskin: thank you for being patient since %.f seconds ",
|
||||
"\rcdrskin: thank you for being patient for %.f seconds ",
|
||||
elapsed_total_time);
|
||||
}
|
||||
advance_interval= 1;
|
||||
@ -8028,11 +8032,15 @@ int Cdrskin_create(struct CdrskiN **o, struct CdrpreskiN **preskin,
|
||||
printf("cdrskin: scanning for devices ...\n");
|
||||
fflush(stdout);
|
||||
|
||||
#ifdef Cdrskin_libburn_has_burn_msgS
|
||||
if(skin->preskin->verbosity<Cdrskin_verbose_debuG)
|
||||
burn_msgs_set_severities("NEVER", "NOTE", "cdrskin: ");
|
||||
#endif
|
||||
|
||||
/* In cdrskin there is not much sense in queueing library messages.
|
||||
It is done here only for testing it from time to time */
|
||||
Cdrpreskin_queue_msgs(skin->preskin,1);
|
||||
|
||||
|
||||
#ifndef Cdrskin_oldfashioned_api_usE
|
||||
if(stdio_drive) {
|
||||
ret= burn_drive_scan_and_grab(&(skin->drives),skin->preskin->device_adr,0);
|
||||
@ -8053,6 +8061,11 @@ int Cdrskin_create(struct CdrskiN **o, struct CdrpreskiN **preskin,
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef Cdrskin_libburn_has_burn_msgS
|
||||
burn_msgs_set_severities(skin->preskin->queue_severity,
|
||||
skin->preskin->print_severity, "cdrskin: ");
|
||||
#endif
|
||||
|
||||
/* This prints the eventual queued messages */
|
||||
Cdrpreskin_queue_msgs(skin->preskin,0);
|
||||
|
||||
|
@ -57,9 +57,9 @@ and to MMC-5 for DVD or BD).
|
||||
GPL software included:<BR>
|
||||
</H2>
|
||||
<DL>
|
||||
<DT>libburn-0.4.8</DT>
|
||||
<DT>libburn-0.5.4</DT>
|
||||
<DD>(founded by Derek Foreman and Ben Jansens,
|
||||
furthered by team of libburnia-project.org)</DD>
|
||||
furthered since August 2006 by Thomas Schmitt from team of libburnia-project.org)</DD>
|
||||
<DD>transfers data to CD, DVD, BD-RE</DD>
|
||||
</DL>
|
||||
</P>
|
||||
@ -186,8 +186,8 @@ or to do experiments on BD-R media.
|
||||
<P>
|
||||
<DL>
|
||||
<DT>Download as source code (see README):</DT>
|
||||
<DD><A HREF="cdrskin-0.4.8.pl00.tar.gz">cdrskin-0.4.8.pl00.tar.gz</A>
|
||||
(730 KB).
|
||||
<DD><A HREF="cdrskin-0.5.4.pl00.tar.gz">cdrskin-0.5.4.pl00.tar.gz</A>
|
||||
(740 KB).
|
||||
</DD>
|
||||
<DD>
|
||||
The cdrskin tarballs are source code identical with libburn releases
|
||||
@ -236,16 +236,22 @@ cdrskin_0.4.2.pl00-x86-suse9_0-static.tar.gz</A>, (310 KB), -static compiled,
|
||||
<HR>
|
||||
|
||||
<P>
|
||||
Enhancements towards previous stable version cdrskin-0.4.6.pl00:
|
||||
Enhancements towards previous stable version cdrskin-0.5.2.pl00:
|
||||
<UL>
|
||||
<LI>Most SCSI errors now get reported with message texts as of MMC-5</LI>
|
||||
<!--
|
||||
<LI>none</LI>
|
||||
-->
|
||||
</UL>
|
||||
|
||||
<!--
|
||||
-->
|
||||
Bug fixes towards cdrskin-0.4.6.pl00:
|
||||
Bug fixes towards cdrskin-0.5.2.pl00:
|
||||
<UL>
|
||||
<LI>Random access addressing for DVD-RAM and BD-RE did not work</LI>
|
||||
<LI>
|
||||
dev=/dev/srN or dev=/dev/scdN on Linux 2.4 was not converted into dev=/dev/sgM
|
||||
</LI>
|
||||
<!--
|
||||
<LI>none</LI>
|
||||
-->
|
||||
</UL>
|
||||
|
||||
</P>
|
||||
@ -254,8 +260,8 @@ Bug fixes towards cdrskin-0.4.6.pl00:
|
||||
|
||||
<P>
|
||||
<DL>
|
||||
<DT><H3>Development snapshot, version 0.4.9 :</H3></DT>
|
||||
<DD>Enhancements towards current stable version 0.4.8.pl00:
|
||||
<DT><H3>Development snapshot, version 0.5.5 :</H3></DT>
|
||||
<DD>Enhancements towards current stable version 0.5.4.pl00:
|
||||
<UL>
|
||||
<!--
|
||||
-->
|
||||
@ -264,10 +270,10 @@ Bug fixes towards cdrskin-0.4.6.pl00:
|
||||
</UL>
|
||||
</DD>
|
||||
<DD> </DD>
|
||||
<DD><A HREF="README_cdrskin_devel">README 0.4.9</A>
|
||||
<DD><A HREF="cdrskin__help_devel">cdrskin_0.4.9 --help</A></DD>
|
||||
<DD><A HREF="cdrskin_help_devel">cdrskin_0.4.9 -help</A></DD>
|
||||
<DD><A HREF="man_1_cdrskin_devel.html">man cdrskin (as of 0.4.9)</A></DD>
|
||||
<DD><A HREF="README_cdrskin_devel">README 0.5.5</A>
|
||||
<DD><A HREF="cdrskin__help_devel">cdrskin_0.5.5 --help</A></DD>
|
||||
<DD><A HREF="cdrskin_help_devel">cdrskin_0.5.5 -help</A></DD>
|
||||
<DD><A HREF="man_1_cdrskin_devel.html">man cdrskin (as of 0.5.5)</A></DD>
|
||||
<DD> </DD>
|
||||
<DT>Maintainers of cdrskin unstable packages please use SVN of
|
||||
<A HREF="http://libburnia-project.org"> libburnia-project.org</A></DT>
|
||||
@ -287,8 +293,8 @@ admins with full system souvereignty.</DT>
|
||||
<A HREF="README_cdrskin_devel">upcoming README</A> ):
|
||||
</DD>
|
||||
<DD>
|
||||
<A HREF="cdrskin-0.4.9.tar.gz">cdrskin-0.4.9.tar.gz</A>
|
||||
(730 KB).
|
||||
<A HREF="cdrskin-0.5.5.tar.gz">cdrskin-0.5.5.tar.gz</A>
|
||||
(740 KB).
|
||||
</DD>
|
||||
|
||||
<!-- This is not offered any more since spring 2008
|
||||
@ -329,14 +335,33 @@ provide libburn with invaluable examples on how to deal with DVD media.
|
||||
<A NAME="examples">
|
||||
<P>
|
||||
<DL>
|
||||
<DT>Example for a setup of device permissions. To be done by the superuser:</DT>
|
||||
<DT>(CD devices which offer no rw-permission are invisible to normal users.)
|
||||
<DT>Example for a setup of device permissions.</DT>
|
||||
<DT>
|
||||
Newer Linux distros enable rw-access for the desktop user automatically.
|
||||
So try as normal user whether all your drives are found.
|
||||
CD devices which offer no rw-permission will stay invisible.
|
||||
</DT>
|
||||
<DD>$ <KBD><B>cdrskin --devices</B></KBD></DD>
|
||||
<DT>If not all desired drives show up, become superuser and do again:</DT>
|
||||
</DT>
|
||||
<DD># <KBD><B>cdrskin --devices</B></KBD></DD>
|
||||
<DD><KBD>...</KBD></DD>
|
||||
<DD><KBD>0 dev='/dev/sr0' rwrwr- : 'TEAC' 'CD-ROM CD-532S'</KBD></DD>
|
||||
<DD><KBD>0 dev='/dev/sr0' rwr-r- : 'TEAC' 'CD-ROM CD-532S'</KBD></DD>
|
||||
<DD><KBD>1 dev='/dev/hdc' rwrw-- : 'LITE-ON' 'LTR-48125S'</KBD></DD>
|
||||
<DT>Most simple and most insecure is this equivalent
|
||||
of the usual cdrecord permissions u+s,a+x:</DT>
|
||||
<DD># <KBD><B>chmod a+rw /dev/sr0 /dev/hdc</B></KBD></DD>
|
||||
<DT>
|
||||
More secure is to put the permitted users into a group like
|
||||
"floppy", to assign /dev/sr0 /dev/hdc to this group,
|
||||
and to allow rw-access only to group members.
|
||||
</DT>
|
||||
<DD># <KBD><B>vi /etc/group</B></KBD></DD>
|
||||
<DD><KBD>...</KBD></DD>
|
||||
<DD><KBD>floppy:x:19:thomas,scdbackup</KBD></DD>
|
||||
<DD><KBD>...</KBD></DD>
|
||||
<DD># <KBD><B>chgrp floppy /dev/sr0 /dev/hdc</B></KBD></DD>
|
||||
<DD># <KBD><B>chmod g+rw /dev/sr0 /dev/hdc</B></KBD></DD>
|
||||
</DL>
|
||||
</P>
|
||||
|
||||
|
@ -1 +1 @@
|
||||
#define Cdrskin_timestamP "2008.05.17.080001"
|
||||
#define Cdrskin_timestamP "2008.10.05.073001"
|
||||
|
@ -5546,7 +5546,7 @@ Made number transition to 0.4.8 and activated development documentation
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_4_9
|
||||
Updated cdrskin tarball generator
|
||||
|
||||
17 May 2008 []
|
||||
17 May 2008 [1792]
|
||||
cdrskin/changelog.txt
|
||||
Documented changes and release timestamp
|
||||
|
||||
@ -5554,9 +5554,313 @@ Documented changes and release timestamp
|
||||
* Bug fix: random access addressing for DVD-RAM and BD-RE did not work
|
||||
|
||||
|
||||
2008.05.17.115434 [1790]
|
||||
Makefile.am
|
||||
configure.ac
|
||||
README
|
||||
libburn/libburn.h
|
||||
cdrskin/cdrskin.c
|
||||
cdrskin/README
|
||||
cdrskin/compile_cdrskin.sh
|
||||
cdrskin/cdrskin_timestamp.h
|
||||
cdrskin/cdrskin_eng.html
|
||||
cdrskin/cdrskin.1
|
||||
Made number transition to 0.4.9
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.4.9 -
|
||||
------------------------------------ cycle - cdrskin-0.4.9 -
|
||||
17 May 2008 [1791]
|
||||
- cdrskin/add_ts_changes_to_libburn_0_4_6
|
||||
- cdrskin/add_ts_changes_to_libburn_0_4_7
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_4_8
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_4_9
|
||||
Updated cdrskin tarball generator
|
||||
|
||||
17 May 2008 [1793]
|
||||
cdrskin/changelog.txt
|
||||
Documented changes and release timestamp
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.4.9 - 2008.05.17.121250
|
||||
|
||||
14 Jun 2008 [1852]
|
||||
README
|
||||
Updated release history
|
||||
|
||||
2008.06.14.140711 [1853]
|
||||
libburn/libburn.h
|
||||
Inserted @since tags for all functions older than 0.2.0
|
||||
|
||||
2008.07.02.093933 [1882]
|
||||
libburn/sg-linux.c
|
||||
With auto device family: scd is now fallback if sr does not exist
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.4.9 - 2008.07.12.164045
|
||||
* Ability to use /dev/scd as fallback if /dev/sr does not exist
|
||||
* Bug fix: option drive_scsi_dev_family=scd lead to buffer overflow
|
||||
|
||||
|
||||
2008.07.14.112935 [1914]
|
||||
libburn/sg-linux.c
|
||||
libburn/libdax_msgs.h
|
||||
Trying to avoid SORRY messages when hitting busy hard disk /dev/hdX
|
||||
|
||||
2008.07.14.113050 [1915]
|
||||
cdrskin/cdrskin.c
|
||||
Making visible the new NOTE and HINT about busy alleged hard disks
|
||||
|
||||
2008.07.14.113152 [1916]
|
||||
configure.ac
|
||||
Did LT_CURRENT++, LT_AGE++ because of new API call
|
||||
|
||||
2008.07.14.113903 [1917]
|
||||
libburn/libburn.h
|
||||
libburn/file.c
|
||||
libburn/async.c
|
||||
New API call burn_fifo_peek_data()
|
||||
|
||||
2008.07.14.164528 [1922]
|
||||
libburn/sg-linux.c
|
||||
Followed hint of Giulio Orsero to recognize disk by /proc/ide/hdX/media
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.4.9 - 2008.07.14.164906
|
||||
* New API call burn_fifo_peek_data()
|
||||
|
||||
2008.07.16.070001 [1927]
|
||||
Makefile.am
|
||||
configure.ac
|
||||
README
|
||||
libburn/libburn.h
|
||||
cdrskin/cdrskin.c
|
||||
cdrskin/README
|
||||
cdrskin/compile_cdrskin.sh
|
||||
cdrskin/cdrskin_timestamp.h
|
||||
cdrskin/cdrskin_eng.html
|
||||
Made number transition to 0.5.0 and activated development documentation
|
||||
|
||||
16 Jul 2008 [1928]
|
||||
- cdrskin/add_ts_changes_to_libburn_0_4_8
|
||||
- cdrskin/add_ts_changes_to_libburn_0_4_9
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_0
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_1
|
||||
Updated cdrskin tarball generator
|
||||
|
||||
16 Jul 2008 [1929]
|
||||
cdrskin/changelog.txt
|
||||
Documented changes and release timestamp
|
||||
|
||||
------------------------------ release - cdrskin-0.5.0.pl00 - 2008.07.16.070001
|
||||
* Ability to use /dev/scd as fallback if /dev/sr does not exist
|
||||
* Bug fix: option drive_scsi_dev_family=scd lead to buffer overflow
|
||||
* New API call burn_fifo_peek_data()
|
||||
|
||||
|
||||
2008.07.16.090816 [1930]
|
||||
Makefile.am
|
||||
configure.ac
|
||||
README
|
||||
libburn/libburn.h
|
||||
cdrskin/cdrskin.c
|
||||
cdrskin/README
|
||||
cdrskin/compile_cdrskin.sh
|
||||
cdrskin/cdrskin_timestamp.h
|
||||
cdrskin/cdrskin_eng.html
|
||||
Made number transition to 0.5.1 and activated development documentation
|
||||
|
||||
16 Jul 2008 [1931]
|
||||
- cdrskin/add_ts_changes_to_libburn_0_4_8
|
||||
- cdrskin/add_ts_changes_to_libburn_0_4_9
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_0
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_1
|
||||
Updated cdrskin tarball generator
|
||||
|
||||
16 Jul 2008 [1932]
|
||||
cdrskin/changelog.txt
|
||||
Documented changes and release timestamp
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.5.1 - 2008.07.14.164528
|
||||
|
||||
|
||||
2008.08.01.101053 [1954]
|
||||
libburn/drive.h
|
||||
libburn/drive.c
|
||||
libburn/sg-linux.c
|
||||
Avoiding drive scan if single drive is given
|
||||
|
||||
2008.08.05.175930 [1963]
|
||||
libburn/os-linux.h
|
||||
libburn/drive.h
|
||||
libburn/drive.c
|
||||
libburn/sg-linux.c
|
||||
libburn/libdax_msgs.h
|
||||
cdrskin/cdrskin.1
|
||||
Taking into respect drive list from /proc/sys/dev/cdrom/info
|
||||
|
||||
5 Aug 2008 [1964]
|
||||
cdrskin/cdrskin_eng.html
|
||||
Updated for next 0.5.1 cycle
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.5.1 -
|
||||
* Larger set of possibly acceptable drive device file names
|
||||
|
||||
|
||||
2008.08.09.071742 [1975]
|
||||
libburn/mmc.c
|
||||
libburn/structure.h
|
||||
libburn/structure.c
|
||||
CD burn_toc_entries now bear extension_valid data
|
||||
|
||||
2008.08.09.071854 [1976]
|
||||
libburn/libburn.h
|
||||
libburn/read.c
|
||||
New flag bit2 with burn_read_data()
|
||||
|
||||
2008.08.19.122535 [1991]
|
||||
libburn/libburn.h
|
||||
API clarification about CD burn_toc_entries
|
||||
|
||||
2008.08.19.123513 [1992]
|
||||
libburn/structure.c
|
||||
Reacted on harmless compiler warning
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.5.1 - 2008.08.19.123513
|
||||
|
||||
2008.08.20.080001 [1994]
|
||||
Makefile.am
|
||||
configure.ac
|
||||
README
|
||||
libburn/libburn.h
|
||||
cdrskin/cdrskin.c
|
||||
cdrskin/README
|
||||
cdrskin/compile_cdrskin.sh
|
||||
cdrskin/cdrskin_timestamp.h
|
||||
cdrskin/cdrskin_eng.html
|
||||
Made number transition to 0.5.2 and activated development documentation
|
||||
|
||||
20 Aug 2008 [1995]
|
||||
- cdrskin/add_ts_changes_to_libburn_0_5_0
|
||||
- cdrskin/add_ts_changes_to_libburn_0_5_1
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_2
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_3
|
||||
Updated cdrskin tarball generator
|
||||
|
||||
20 Aug 2008 [1996]
|
||||
cdrskin/changelog.txt
|
||||
Documented changes and release timestamp
|
||||
|
||||
------------------------------ release - cdrskin-0.5.2.pl00 - 2008.08.20.080001
|
||||
* Larger set of possibly acceptable drive device file names
|
||||
|
||||
2008.08.20.100045 [1997]
|
||||
Makefile.am
|
||||
configure.ac
|
||||
README
|
||||
libburn/libburn.h
|
||||
cdrskin/cdrskin.c
|
||||
cdrskin/README
|
||||
cdrskin/compile_cdrskin.sh
|
||||
cdrskin/cdrskin_timestamp.h
|
||||
cdrskin/cdrskin_eng.html
|
||||
Made number transition to 0.5.3
|
||||
|
||||
20 Aug 2008 [1998]
|
||||
- cdrskin/add_ts_changes_to_libburn_0_5_0
|
||||
- cdrskin/add_ts_changes_to_libburn_0_5_1
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_2
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_3
|
||||
Updated cdrskin tarball generator
|
||||
|
||||
20 Aug 2008 [1999]
|
||||
cdrskin/changelog.txt
|
||||
Documented changes and release timestamp
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.5.3 - 2008.08.20.110457
|
||||
|
||||
30 Aug 2008 [2023]
|
||||
README
|
||||
Mentioned release of libisoburn-0.2.4
|
||||
|
||||
2008.08.30.104339 [2024]
|
||||
libburn/mmc.c
|
||||
libburn/spc.c
|
||||
Issueing many SCSI error messages in cleartext now
|
||||
|
||||
2008.09.09.131915 [2039]
|
||||
libburn/sg-linux.c
|
||||
Trying to avoid unnecessary access to sibling device objects
|
||||
|
||||
12 Sep 2008 [2043]
|
||||
doc/cookbook.txt
|
||||
Described ISO 9660 multi-session on overwriteable media
|
||||
|
||||
2008.09.14.174344 [2048]
|
||||
libburn/util.c
|
||||
Gave up problematic and unused version.h
|
||||
|
||||
2008.09.16.060250 [2052]
|
||||
cdrskin/cdrskin.c
|
||||
Corrected pacifier text (Ticket 141)
|
||||
|
||||
24 Sep 2008 [2079]
|
||||
README
|
||||
Mentioned recent releases of libisofs and libisoburn
|
||||
|
||||
2008.09.28.193802 [2086]
|
||||
libburn/spc.c
|
||||
Bug fix: Potential buffer overflow introduced with revision 2024
|
||||
|
||||
2008.09.28.211741 [2087]
|
||||
libburn/sg-linux.c
|
||||
Bug fix: /dev/sr0 was accepted as enumerable address on Linux 2.4
|
||||
|
||||
2008.10.04.072657 [2096]
|
||||
libburn/write.c
|
||||
libburn/read.c
|
||||
libburn/drive.c
|
||||
Prevented SIGSEGV after illegal drive operations during sync write
|
||||
|
||||
2008.10.04.072657 [2097]
|
||||
cdrskin/cdrskin.1
|
||||
Mentioned new xorriso capabilities in man cdrskin
|
||||
|
||||
2008.10.04.073814 [2098]
|
||||
configure.ac
|
||||
Incremented LT_CURRENT and LT_AGE to get libburn.so.4.18.0
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.5.3 - 2008.10.04.072657
|
||||
* Bug fix: /dev/sr0 was accepted as enumerable address on Linux 2.4
|
||||
|
||||
|
||||
2008.10.05.073001 [2102]
|
||||
Makefile.am
|
||||
configure.ac
|
||||
README
|
||||
libburn/libburn.h (burn_header_version_*)
|
||||
cdrskin/cdrskin.c
|
||||
cdrskin/README
|
||||
cdrskin/compile_cdrskin.sh
|
||||
cdrskin/cdrskin_timestamp.h
|
||||
cdrskin/wiki_plain.txt
|
||||
cdrskin/cdrskin_eng.html
|
||||
doc/comments
|
||||
Made number transition
|
||||
|
||||
5 Oct 2008 [2103]
|
||||
- cdrskin/add_ts_changes_to_libburn_0_5_2
|
||||
- cdrskin/add_ts_changes_to_libburn_0_5_3
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_4
|
||||
+ cdrskin/add_ts_changes_to_libburn_0_5_5
|
||||
Updated cdrskin tarball generator
|
||||
|
||||
5 Oct 2008 []
|
||||
cdrskin/changelog.txt
|
||||
Documented changes and release timestamp
|
||||
|
||||
------------------------------ release - cdrskin-0.5.4.pl00 - 2008.10.06.073001
|
||||
* Bug fix: /dev/sr0 was accepted as enumerable address on Linux 2.4
|
||||
* Issueing many SCSI error messages in cleartext now
|
||||
|
||||
|
||||
------------------------------------ cycle - cdrskin-0.5.5 -
|
||||
------------------------------------ cycle - cdrskin-0.5.5 -
|
||||
------------------------------------ cycle - cdrskin-0.5.5 -
|
||||
|
||||
===============================================================================
|
||||
TODO
|
||||
@ -5565,6 +5869,8 @@ Documented changes and release timestamp
|
||||
|
||||
--------------------------------- bugs -------------------------------------
|
||||
|
||||
- Do something about drive->buffer asynchronous race conditions
|
||||
and dangerous use of local heap memory
|
||||
|
||||
- Why are DVD+R tracks labeled "invisible" by dvd+rw-mediainfo ?
|
||||
Why does the DVD drive only show the first session ?
|
||||
@ -5578,9 +5884,11 @@ READ TRACK INFORMATION[#5]:
|
||||
|
||||
------------------------------ end of bugs ---------------------------------
|
||||
|
||||
provide DVD+R DL layer break setter
|
||||
Enable profile 0x41 BD-R sequential recording (much like DVD+R)
|
||||
|
||||
@since tags
|
||||
? Enable profile 0x42 BD-R random recording
|
||||
|
||||
Provide DVD+R DL layer break setter
|
||||
|
||||
Check all SORRY and FATAL errors whether they should become FAILUREs
|
||||
|
||||
@ -5622,10 +5930,6 @@ http://developer.osdl.org/dev/robustmutexes/src/fusyn.hg/Documentation/ioctl/cdr
|
||||
[]
|
||||
Convert burn_print() into libdax_msgs_submit()
|
||||
|
||||
[]
|
||||
Test unlocking of all drives by burn_drive_info_free()
|
||||
Test unlocking of single drive by burn_drive_grab(), burn_drive_release()
|
||||
|
||||
[]
|
||||
Clear outdated persistent read buffer after small CD image was read (ticket 57)
|
||||
|
||||
|
@ -7,7 +7,7 @@
|
||||
debug_opts="-O2"
|
||||
def_opts=
|
||||
largefile_opts="-D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE=1"
|
||||
libvers="-DCdrskin_libburn_0_4_8"
|
||||
libvers="-DCdrskin_libburn_0_5_4"
|
||||
cleanup_src_or_obj="libburn/cleanup.o"
|
||||
libdax_msgs_o="libburn/libdax_msgs.o"
|
||||
libdax_audioxtr_o="libburn/libdax_audioxtr.o"
|
||||
@ -33,15 +33,15 @@ do
|
||||
libdax_audioxtr_o=
|
||||
libdax_msgs_o="libburn/message.o"
|
||||
cleanup_src_or_obj="-DCleanup_has_no_libburn_os_H cdrskin/cleanup.c"
|
||||
elif test "$i" = "-libburn_0_4_8"
|
||||
elif test "$i" = "-libburn_0_5_4"
|
||||
then
|
||||
libvers="-DCdrskin_libburn_0_4_8"
|
||||
libvers="-DCdrskin_libburn_0_5_4"
|
||||
libdax_audioxtr_o="libburn/libdax_audioxtr.o"
|
||||
libdax_msgs_o="libburn/libdax_msgs.o"
|
||||
cleanup_src_or_obj="libburn/cleanup.o"
|
||||
elif test "$i" = "-libburn_svn"
|
||||
then
|
||||
libvers="-DCdrskin_libburn_0_4_9"
|
||||
libvers="-DCdrskin_libburn_0_5_5"
|
||||
libdax_audioxtr_o="libburn/libdax_audioxtr.o"
|
||||
libdax_msgs_o="libburn/libdax_msgs.o"
|
||||
cleanup_src_or_obj="libburn/cleanup.o"
|
||||
@ -76,7 +76,7 @@ do
|
||||
echo " -compile_cdrfifo compile program cdrskin/cdrfifo."
|
||||
echo " -compile_dewav compile program test/dewav without libburn."
|
||||
echo " -cvs_A60220 set macro to match libburn-CVS of 20 Feb 2006."
|
||||
echo " -libburn_0_4_8 set macro to match libburn-0.4.8."
|
||||
echo " -libburn_0_5_4 set macro to match libburn-0.5.4"
|
||||
echo " -libburn_svn set macro to match current libburn-SVN."
|
||||
echo " -no_largefile do not use 64 bit off_t (must match libburn)."
|
||||
echo " -do_not_compile_cdrskin omit compilation of cdrskin/cdrskin."
|
||||
|
22
configure.ac
22
configure.ac
@ -1,4 +1,4 @@
|
||||
AC_INIT([libburn], [0.4.8], [http://libburnia-project.org])
|
||||
AC_INIT([libburn], [0.5.4], [http://libburnia-project.org])
|
||||
AC_PREREQ([2.50])
|
||||
dnl AC_CONFIG_HEADER([config.h])
|
||||
|
||||
@ -62,6 +62,9 @@ dnl 0.4.2 = libburn.so.4.7.0
|
||||
dnl 0.4.4 = libburn.so.4.9.0
|
||||
dnl 0.4.6 = libburn.so.4.11.0
|
||||
dnl 0.4.8 = libburn.so.4.13.0
|
||||
dnl 0.5.0 = libburn.so.4.15.0
|
||||
dnl 0.5.2 = libburn.so.4.17.0
|
||||
dnl 0.5.4 = libburn.so.4.19.0
|
||||
dnl
|
||||
dnl So LT_CURRENT, LT_REVISION and LT_AGE get set directly here.
|
||||
dnl SONAME of the emerging library is LT_CURRENT - LT_AGE.
|
||||
@ -86,8 +89,8 @@ dnl If BURN_*_VERSION changes, be sure to change AC_INIT above to match.
|
||||
dnl
|
||||
dnl As said: Only copies. Original in libburn/libburn.h : burn_header_version_*
|
||||
BURN_MAJOR_VERSION=0
|
||||
BURN_MINOR_VERSION=4
|
||||
BURN_MICRO_VERSION=8
|
||||
BURN_MINOR_VERSION=5
|
||||
BURN_MICRO_VERSION=4
|
||||
BURN_VERSION=$BURN_MAJOR_VERSION.$BURN_MINOR_VERSION.$BURN_MICRO_VERSION
|
||||
|
||||
AC_SUBST(BURN_MAJOR_VERSION)
|
||||
@ -98,15 +101,16 @@ AC_SUBST(BURN_VERSION)
|
||||
dnl Libtool versioning
|
||||
LT_RELEASE=$BURN_MAJOR_VERSION.$BURN_MINOR_VERSION.$BURN_MICRO_VERSION
|
||||
dnl
|
||||
dnl ts A80517
|
||||
dnl This is the release version libburn-0.4.8 = libburn.so.4.13.0
|
||||
dnl ### This is the development version after above release version
|
||||
dnl ts A80820
|
||||
dnl ### This is the release version libburn-0.5.2 = libburn.so.4.17.0
|
||||
dnl This is the development version after above release version
|
||||
dnl ### LT_CURRENT++, LT_AGE++ has not yet happened.
|
||||
dnl LT_CURRENT++, LT_AGE++ has happened meanwhile.
|
||||
dnl
|
||||
dnl SONAME = 17 - 13 = 4 . Library name = libburn.so.4.13.0
|
||||
LT_CURRENT=17
|
||||
dnl SONAME = 23 - 19 = 4 . Library name = libburn.so.4.19.0
|
||||
LT_CURRENT=23
|
||||
LT_AGE=19
|
||||
LT_REVISION=0
|
||||
LT_AGE=13
|
||||
LT_CURRENT_MINUS_AGE=`expr $LT_CURRENT - $LT_AGE`
|
||||
|
||||
AC_SUBST(LT_RELEASE)
|
||||
|
@ -432,6 +432,10 @@ The recipes described here are depending on formatting state:
|
||||
- DVD-RAM and BD-RE formatting
|
||||
- DVD-RAM and BD-RE speed tuning
|
||||
|
||||
Slightly off topic are
|
||||
- ISO 9660 multi-session emulation on overwriteable media
|
||||
- ISO 9660 based TOC emulation on overwriteable media
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Overwriting in general :
|
||||
|
||||
@ -522,7 +526,7 @@ with Close Function 010b despite there is no session open in this scenario.)
|
||||
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
Unformatted DVD+RW
|
||||
Unformatted DVD+RW :
|
||||
|
||||
This is the state of previously unused DVD+RW media.
|
||||
|
||||
@ -762,6 +766,76 @@ Nevertheless it worked on all tested drives is proper alignment was observed.
|
||||
(mmc5r03c.pdf 5.4.13, 6.45)
|
||||
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
ISO 9660 multi-session emulation on overwriteable media :
|
||||
|
||||
Overwriteable media provide a single overwriteable track which may grow up to
|
||||
the full media capacity. There is no builtin table-of-content which records
|
||||
the history of write sessions.
|
||||
mount -t iso9660 will use sbsector=0 as default.
|
||||
The term "superblock" shall depict the first 64 KiB after the sbsector address.
|
||||
|
||||
ISO 9660 multi-session depends on typical TOC information in two ways:
|
||||
It needs the superblock address MSC1 of the most recently recorded session and
|
||||
it needs the Next Writeable Address NWA for which to prepare the adress offset.
|
||||
|
||||
The following is learned from growisofs and from ECMA-119:
|
||||
http://www.ecma-international.org/publications/files/ECMA-ST/Ecma-119.pdf
|
||||
|
||||
ISO 9660 filesystems provide information about the number of sectors which
|
||||
is also the lowest unused block address and thus a suitable NWA.
|
||||
This block address is stored in the Primary Volume Descriptor which is supposed
|
||||
to be stored in block 16 (eventually relative to MSC1).
|
||||
The bytes 0 to 5 of a PVD block are
|
||||
0x01 'C' 'D' '0' '0' '1'
|
||||
The sector count can then be read from byte 80 to 83
|
||||
sectors= pvd[80] | (pvd[81] << 8) | (pvd[82] << 16) | (pvd[83] << 24);
|
||||
To support CD, DVD and BD media alike, it is advisable to round the NWA
|
||||
to the next multiple of 32 (= 64 KiB).
|
||||
(Ecma-119.pdf 8.4)
|
||||
|
||||
So one can use 0 as MSC1 and prepare a new ISO session for the computed NWA.
|
||||
After writing the session it is necessary to patch the PVD at LBA 16.
|
||||
The minimal change would be to update the number of image sectors.
|
||||
It is stored in both notations LSB and MSB:
|
||||
for(i= 0; i < 4; i++)
|
||||
pvd[87 - i]= pvd[80 + i]= (sectors >> (8 * i)) & 0xff;
|
||||
|
||||
cdrskin --grow_overwriteable not only patches the sector fields of the
|
||||
PVD block but also the blocks up to LBA 31 which begin with
|
||||
0xff 'C' 'D' '0' '0' '1'
|
||||
libisoburn submits 64 KiB data buffer to libisofs before image generation and
|
||||
afterwards writes these 64 KiB as new superblock to LBA 0.
|
||||
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
ISO 9660 based TOC emulation on overwriteable media :
|
||||
|
||||
Above method of multi-session emulation yields a single session image after
|
||||
each add-on session. No reliable session history can be read because the
|
||||
sector size of the existing session gets overwritten by the new one.
|
||||
A TOC with session history is nevertheless desirable with incremental backups
|
||||
in order to access older backup states by mounting older superblocks at the
|
||||
start addresses of older sessions.
|
||||
|
||||
All usual ISO 9660 formatter programs write a complete superblock to the
|
||||
start of each session.
|
||||
With a uniform NWA rounding rule it is possible to compute the address of
|
||||
superblock N+1 as the NWA after session N. The only problem is N=1
|
||||
because it gets overwritten by later sessions.
|
||||
|
||||
libisoburn preserves the information of session 1 by writing the first session
|
||||
to LBA 32 rather than LBA 0. Afterwards it writes the overall superblock to
|
||||
LBA 0 (up to 31).
|
||||
So with all further add-on sessions the superblock at LBA 0 will enclose the
|
||||
overall image, while the superblocks of the sessions form a chain beginning
|
||||
at LBA 32. Each session superblock points to the next one by its sector count
|
||||
rounded up to 32. The chain end is marked by the overall image size.
|
||||
This chain gives the start addresses of sessions. The sector count minus start
|
||||
address gives the size of a particular session. ECMA-119 explains how to
|
||||
retrieve more info from the PVD (e.g. the volume id).
|
||||
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
||||
-------------------------------------------------------------------------------
|
||||
|
@ -38,7 +38,7 @@ PROJECT_NUMBER = @PACKAGE_VERSION@
|
||||
# If a relative path is entered, it will be relative to the location
|
||||
# where doxygen was started. If left blank the current directory will be used.
|
||||
|
||||
OUTPUT_DIRECTORY =
|
||||
OUTPUT_DIRECTORY = @abs_top_builddir@
|
||||
|
||||
# If the CREATE_SUBDIRS tag is set to YES, then doxygen will create
|
||||
# 4096 sub-directories (in 2 levels) under the output directory of each output
|
||||
@ -104,7 +104,7 @@ INLINE_INHERITED_MEMB = NO
|
||||
# path before files name in the file list and in the header files. If set
|
||||
# to NO the shortest path that makes the file name unique will be used.
|
||||
|
||||
FULL_PATH_NAMES = YES
|
||||
FULL_PATH_NAMES = NO
|
||||
|
||||
# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag
|
||||
# can be used to strip a user-defined part of the path. Stripping is
|
||||
@ -113,7 +113,7 @@ FULL_PATH_NAMES = YES
|
||||
# If left blank the directory from which doxygen is run is used as the
|
||||
# path to strip.
|
||||
|
||||
STRIP_FROM_PATH = @top_srcdir@
|
||||
STRIP_FROM_PATH =
|
||||
|
||||
# The STRIP_FROM_INC_PATH tag can be used to strip a user-defined part of
|
||||
# the path mentioned in the documentation of a class, which tells
|
||||
|
@ -43,7 +43,15 @@
|
||||
#include "libdax_msgs.h"
|
||||
extern struct libdax_msgs *libdax_messenger;
|
||||
|
||||
#define SCAN_GOING() (workers && !workers->drive)
|
||||
/* ts A80714 : introduced type codes for the worker list */
|
||||
#define Burnworker_type_scaN 0
|
||||
#define Burnworker_type_erasE 1
|
||||
#define Burnworker_type_formaT 2
|
||||
#define Burnworker_type_writE 3
|
||||
#define Burnworker_type_fifO 4
|
||||
|
||||
#define SCAN_GOING() (workers != NULL && \
|
||||
workers->w_type == Burnworker_type_scaN)
|
||||
|
||||
typedef void *(*WorkerFunc) (void *);
|
||||
|
||||
@ -85,6 +93,9 @@ struct fifo_opts
|
||||
|
||||
struct w_list
|
||||
{
|
||||
/* ts A80714 */
|
||||
int w_type; /* see above define Burnworker_type_* */
|
||||
|
||||
struct burn_drive *drive;
|
||||
pthread_t thread;
|
||||
|
||||
@ -113,7 +124,8 @@ static struct w_list *find_worker(struct burn_drive *d)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void add_worker(struct burn_drive *d, WorkerFunc f, void *data)
|
||||
static void add_worker(int w_type, struct burn_drive *d,
|
||||
WorkerFunc f, void *data)
|
||||
{
|
||||
struct w_list *a;
|
||||
struct w_list *tmp;
|
||||
@ -124,6 +136,7 @@ static void add_worker(struct burn_drive *d, WorkerFunc f, void *data)
|
||||
#endif
|
||||
|
||||
a = malloc(sizeof(struct w_list));
|
||||
a->w_type = w_type;
|
||||
a->drive = d;
|
||||
a->u = *(union w_list_data *)data;
|
||||
|
||||
@ -259,7 +272,8 @@ drive_is_active:;
|
||||
o.drives = drives;
|
||||
o.n_drives = n_drives;
|
||||
o.done = 0;
|
||||
add_worker(NULL, (WorkerFunc) scan_worker_func, &o);
|
||||
add_worker(Burnworker_type_scaN, NULL,
|
||||
(WorkerFunc) scan_worker_func, &o);
|
||||
} else if (workers->u.scan.done) {
|
||||
/* its done */
|
||||
ret = workers->u.scan.done;
|
||||
@ -303,7 +317,7 @@ void burn_disc_erase(struct burn_drive *drive, int fast)
|
||||
"NULL pointer caught in burn_disc_erase", 0, 0);
|
||||
return;
|
||||
}
|
||||
if ((SCAN_GOING()) || find_worker(drive)) {
|
||||
if ((SCAN_GOING()) || find_worker(drive) != NULL) {
|
||||
libdax_msgs_submit(libdax_messenger, drive->global_index,
|
||||
0x00020102,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_HIGH,
|
||||
@ -343,7 +357,8 @@ void burn_disc_erase(struct burn_drive *drive, int fast)
|
||||
|
||||
o.drive = drive;
|
||||
o.fast = fast;
|
||||
add_worker(drive, (WorkerFunc) erase_worker_func, &o);
|
||||
add_worker(Burnworker_type_erasE, drive,
|
||||
(WorkerFunc) erase_worker_func, &o);
|
||||
}
|
||||
|
||||
|
||||
@ -364,7 +379,7 @@ void burn_disc_format(struct burn_drive *drive, off_t size, int flag)
|
||||
int ok = 0;
|
||||
char msg[160];
|
||||
|
||||
if ((SCAN_GOING()) || find_worker(drive)) {
|
||||
if ((SCAN_GOING()) || find_worker(drive) != NULL) {
|
||||
libdax_msgs_submit(libdax_messenger, drive->global_index,
|
||||
0x00020102,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_HIGH,
|
||||
@ -411,7 +426,8 @@ void burn_disc_format(struct burn_drive *drive, off_t size, int flag)
|
||||
o.drive = drive;
|
||||
o.size = size;
|
||||
o.flag = flag;
|
||||
add_worker(drive, (WorkerFunc) format_worker_func, &o);
|
||||
add_worker(Burnworker_type_formaT, drive,
|
||||
(WorkerFunc) format_worker_func, &o);
|
||||
}
|
||||
|
||||
|
||||
@ -441,7 +457,7 @@ void burn_disc_write(struct burn_write_opts *opts, struct burn_disc *disc)
|
||||
/* ts A61006 */
|
||||
/* a ssert(!SCAN_GOING()); */
|
||||
/* a ssert(!find_worker(opts->drive)); */
|
||||
if ((SCAN_GOING()) || find_worker(opts->drive)) {
|
||||
if ((SCAN_GOING()) || find_worker(opts->drive) != NULL) {
|
||||
libdax_msgs_submit(libdax_messenger, opts->drive->global_index,
|
||||
0x00020102,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_HIGH,
|
||||
@ -495,7 +511,8 @@ void burn_disc_write(struct burn_write_opts *opts, struct burn_disc *disc)
|
||||
|
||||
opts->refcount++;
|
||||
|
||||
add_worker(opts->drive, (WorkerFunc) write_disc_worker_func, &o);
|
||||
add_worker(Burnworker_type_writE, opts->drive,
|
||||
(WorkerFunc) write_disc_worker_func, &o);
|
||||
}
|
||||
|
||||
|
||||
@ -523,7 +540,8 @@ int burn_fifo_start(struct burn_source *source, int flag)
|
||||
|
||||
o.source = source;
|
||||
o.flag = flag;
|
||||
add_worker(NULL, (WorkerFunc) fifo_worker_func, &o);
|
||||
add_worker(Burnworker_type_fifO, NULL,
|
||||
(WorkerFunc) fifo_worker_func, &o);
|
||||
fs->is_started = 1;
|
||||
return 1;
|
||||
}
|
||||
|
@ -196,6 +196,31 @@ unsigned int burn_drive_count(void)
|
||||
}
|
||||
|
||||
|
||||
/* ts A80801 */
|
||||
int burn_drive_is_listed(char *path, struct burn_drive **found, int flag)
|
||||
{
|
||||
int i, ret;
|
||||
char drive_adr[BURN_DRIVE_ADR_LEN], off_adr[BURN_DRIVE_ADR_LEN];
|
||||
|
||||
ret = burn_drive_convert_fs_adr(path, off_adr);
|
||||
if (ret <= 0)
|
||||
strcpy(off_adr, path);
|
||||
for (i = 0; i <= drivetop; i++) {
|
||||
if (drive_array[i].global_index < 0)
|
||||
continue;
|
||||
ret = burn_drive_d_get_adr(&(drive_array[i]), drive_adr);
|
||||
if (ret <= 0)
|
||||
continue;
|
||||
if(strcmp(off_adr, drive_adr) == 0) {
|
||||
if (found != NULL)
|
||||
*found= &(drive_array[i]);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* ts A61125 : media status aspects of burn_drive_grab() */
|
||||
int burn_drive_inquire_media(struct burn_drive *d)
|
||||
{
|
||||
@ -599,7 +624,7 @@ void burn_disc_format_sync(struct burn_drive *d, off_t size, int flag)
|
||||
int ret, buf_secs, err, i, stages = 1, pbase, pfill, pseudo_sector;
|
||||
off_t num_bufs;
|
||||
char msg[80];
|
||||
struct buffer buf;
|
||||
struct buffer buf, *buf_mem = d->buffer;
|
||||
|
||||
/* reset the progress */
|
||||
d->progress.session = 0;
|
||||
@ -681,7 +706,7 @@ void burn_disc_format_sync(struct burn_drive *d, off_t size, int flag)
|
||||
ex:;
|
||||
d->progress.sector = 0x10000;
|
||||
d->busy = BURN_DRIVE_IDLE;
|
||||
d->buffer = NULL;
|
||||
d->buffer = buf_mem;
|
||||
}
|
||||
|
||||
|
||||
@ -1166,6 +1191,20 @@ int burn_drive_is_banned(char *device_address)
|
||||
}
|
||||
|
||||
|
||||
/* ts A80731 */
|
||||
int burn_drive_whitelist_count(void)
|
||||
{
|
||||
return enumeration_whitelist_top + 1;
|
||||
}
|
||||
|
||||
char *burn_drive_whitelist_item(int idx, int flag)
|
||||
{
|
||||
if (idx < 0 || idx > enumeration_whitelist_top)
|
||||
return NULL;
|
||||
return enumeration_whitelist[idx];
|
||||
}
|
||||
|
||||
|
||||
/* ts A70924 */
|
||||
int burn_drive__fd_from_special_adr(char *adr)
|
||||
{
|
||||
|
@ -125,4 +125,14 @@ int burn_drive__fd_from_special_adr(char *adr);
|
||||
int burn_drive_find_by_thread_pid(struct burn_drive **d, pid_t pid);
|
||||
|
||||
|
||||
/* ts A51221 - A80731 : Whitelist inquiry functions */
|
||||
int burn_drive_is_banned(char *device_address);
|
||||
int burn_drive_whitelist_count(void);
|
||||
char *burn_drive_whitelist_item(int idx, int flag);
|
||||
|
||||
|
||||
/* ts A80801 */
|
||||
int burn_drive_is_listed(char *path, struct burn_drive **found, int flag);
|
||||
|
||||
|
||||
#endif /* __DRIVE */
|
||||
|
@ -540,3 +540,64 @@ int burn_fifo_inquire_status(struct burn_source *source,
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
int burn_fifo_peek_data(struct burn_source *source, char *buf, int bufsize,
|
||||
int flag)
|
||||
{
|
||||
int size, free_bytes, ret, wait_count= 0;
|
||||
char *status_text;
|
||||
struct burn_source_fifo *fs = source->data;
|
||||
|
||||
/* Eventually start fifo thread by reading 0 bytes */
|
||||
ret = fifo_read(source, (unsigned char *) NULL, 0);
|
||||
if (ret<0)
|
||||
return 0;
|
||||
|
||||
/* wait for at least bufsize bytes being ready */
|
||||
while (1) {
|
||||
ret= burn_fifo_inquire_status(source,
|
||||
&size, &free_bytes, &status_text);
|
||||
if (size < bufsize) {
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x0002015c,
|
||||
LIBDAX_MSGS_SEV_FAILURE, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"Fifo size is smaller than desired peek buffer", 0, 0);
|
||||
return -1;
|
||||
}
|
||||
if (fs->out_counter > 0 || (ret & 4) || fs->buf == NULL) {
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x0002015e,
|
||||
LIBDAX_MSGS_SEV_FATAL, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"Fifo is already under consumption when peeking is desired",
|
||||
0, 0);
|
||||
return -1;
|
||||
}
|
||||
if(size - free_bytes >= bufsize) {
|
||||
|
||||
/* <<<
|
||||
fprintf(stderr,
|
||||
"libburn_DEBUG: after waiting cycle %d : fifo %s , %d bytes\n",
|
||||
wait_count, status_text, size - free_bytes);
|
||||
*/
|
||||
|
||||
memcpy(buf, fs->buf, bufsize);
|
||||
return 1;
|
||||
}
|
||||
if (ret&2) { /* input has ended, not enough data arrived */
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x0002015d,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"Fifo input ended short of desired peek buffer size",
|
||||
0, 0);
|
||||
return 0;
|
||||
}
|
||||
usleep(100000);
|
||||
wait_count++;
|
||||
|
||||
/* <<<
|
||||
if(wait_count%10==0)
|
||||
fprintf(stderr,
|
||||
"libburn_DEBUG: waiting cycle %d : fifo %s , %d bytes\n",
|
||||
wait_count, status_text, size - free_bytes);
|
||||
*/
|
||||
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
@ -198,10 +198,12 @@ enum burn_disc_status
|
||||
BURN_DISC_FULL,
|
||||
|
||||
/* ts A61007 */
|
||||
/* @since 0.2.4 */
|
||||
/** The drive was not grabbed when the status was inquired */
|
||||
BURN_DISC_UNGRABBED,
|
||||
|
||||
/* ts A61020 */
|
||||
/* @since 0.2.6 */
|
||||
/** The media seems not to be suitable for burning */
|
||||
BURN_DISC_UNSUITABLE
|
||||
};
|
||||
@ -242,6 +244,7 @@ enum burn_drive_status
|
||||
BURN_DRIVE_GRABBING,
|
||||
|
||||
/* ts A61102 */
|
||||
/* @since 0.2.6 */
|
||||
/** The drive gets written zeroes before the track payload data */
|
||||
BURN_DRIVE_WRITING_PREGAP,
|
||||
/** The drive is told to close a track (TAO only) */
|
||||
@ -250,10 +253,12 @@ enum burn_drive_status
|
||||
BURN_DRIVE_CLOSING_SESSION,
|
||||
|
||||
/* ts A61223 */
|
||||
/* @since 0.3.0 */
|
||||
/** The drive is formatting media */
|
||||
BURN_DRIVE_FORMATTING,
|
||||
|
||||
/* ts A70822 */
|
||||
/* @since 0.4.0 */
|
||||
/** The drive is busy in synchronous read (if you see this then it
|
||||
has been interrupted) */
|
||||
BURN_DRIVE_READING_SYNC,
|
||||
@ -301,12 +306,14 @@ struct burn_toc_entry
|
||||
|
||||
/* Indicates whether extension data are valid and eventually override
|
||||
older elements in this structure:
|
||||
bit0= DVD extension is valid
|
||||
bit0= DVD extension is valid @since 0.3.2
|
||||
@since 0.5.2 : DVD extensions are made valid for CD too
|
||||
*/
|
||||
unsigned char extensions_valid;
|
||||
|
||||
/* ts A70201 : DVD extension.
|
||||
If invalid the members are guaranteed to be 0. */
|
||||
/* @since 0.3.2 */
|
||||
/* Tracks and session numbers are 16 bit. Here are the high bytes. */
|
||||
unsigned char session_msb;
|
||||
unsigned char point_msb;
|
||||
@ -402,6 +409,7 @@ struct burn_source {
|
||||
|
||||
|
||||
/* ts A70125 : BROKE BINARY BACKWARD COMPATIBILITY AT libburn-0.3.1. */
|
||||
/* @since 0.3.2 */
|
||||
/** Program the reply of (*get_size) to a fixed value. It is advised
|
||||
to implement this by a attribute off_t fixed_size; in *data .
|
||||
The read() function does not have to take into respect this fake
|
||||
@ -449,7 +457,7 @@ struct burn_source {
|
||||
|
||||
|
||||
/* ts A71222 : Supposed to be binary backwards compatible extension. */
|
||||
|
||||
/* @since 0.4.2 */
|
||||
/** Valid only if above member .(*read)() is NULL. This indicates a
|
||||
version of struct burn_source younger than 0.
|
||||
From then on, member .version tells which further members exist
|
||||
@ -574,12 +582,14 @@ struct burn_progress {
|
||||
int sector;
|
||||
|
||||
/* ts A61023 */
|
||||
/* @since 0.2.6 */
|
||||
/** The capacity of the drive buffer */
|
||||
unsigned buffer_capacity;
|
||||
/** The free space in the drive buffer (might be slightly outdated) */
|
||||
unsigned buffer_available;
|
||||
|
||||
/* ts A61119 */
|
||||
/* @since 0.2.6 */
|
||||
/** The number of bytes sent to the drive buffer */
|
||||
off_t buffered_bytes;
|
||||
/** The minimum number of bytes stored in buffer during write.
|
||||
@ -591,6 +601,7 @@ struct burn_progress {
|
||||
|
||||
|
||||
/* ts A61226 */
|
||||
/* @since 0.3.0 */
|
||||
/** Description of a speed capability as reported by the drive in conjunction
|
||||
with eventually loaded media. There can be more than one such object per
|
||||
drive. So they are chained via .next and .prev , where NULL marks the end
|
||||
@ -673,6 +684,7 @@ void burn_finish(void);
|
||||
@return 1 ok, all went well
|
||||
0 had to leave a drive in unclean state
|
||||
<0 severe error, do no use libburn again
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_abort(int patience,
|
||||
int (*pacifier_func)(void *handle, int patience, int elapsed),
|
||||
@ -722,6 +734,7 @@ void burn_set_verbosity(int level);
|
||||
@param abort_on_busy Unconditionally abort process when a non blocking
|
||||
exclusive opening attempt indicates a busy drive.
|
||||
Use this only after thorough tests with your app.
|
||||
@since 0.2.2
|
||||
*/
|
||||
void burn_preset_device_open(int exclusive, int blocking, int abort_on_busy);
|
||||
|
||||
@ -735,6 +748,7 @@ void burn_preset_device_open(int exclusive, int blocking, int abort_on_busy);
|
||||
If ever then this call should be done soon after burn_initialize() before
|
||||
any drive scanning.
|
||||
@param yes 1=allow all implemented profiles, 0=only tested media (default)
|
||||
@since 0.3.4
|
||||
*/
|
||||
void burn_allow_untested_profiles(int yes);
|
||||
|
||||
@ -818,17 +832,21 @@ void burn_allow_untested_profiles(int yes);
|
||||
@param load Nonzero to make the drive attempt to load a disc (close its
|
||||
tray door, etc).
|
||||
@return 1 = success , 0 = drive not found , -1 = other error
|
||||
@since 0.2.2
|
||||
*/
|
||||
int burn_drive_scan_and_grab(struct burn_drive_info *drive_infos[],
|
||||
char* adr, int load);
|
||||
|
||||
|
||||
/* ts A51221 */
|
||||
/* @since 0.2.2 */
|
||||
/** Maximum number of particularly permissible drive addresses */
|
||||
#define BURN_DRIVE_WHITELIST_LEN 255
|
||||
|
||||
/** Add a device to the list of permissible drives. As soon as some entry is in
|
||||
the whitelist all non-listed drives are banned from scanning.
|
||||
@return 1 success, <=0 failure
|
||||
@since 0.2.2
|
||||
*/
|
||||
int burn_drive_add_whitelist(char *device_address);
|
||||
|
||||
@ -875,6 +893,7 @@ int burn_drive_scan(struct burn_drive_info *drive_infos[],
|
||||
Use these two only. Further values are to be defined.
|
||||
@return 1 on success, 2 if drive was already forgotten,
|
||||
0 if not permissible, <0 on other failures,
|
||||
@since 0.2.2
|
||||
*/
|
||||
int burn_drive_info_forget(struct burn_drive_info *drive_info, int force);
|
||||
|
||||
@ -887,23 +906,28 @@ void burn_drive_info_free(struct burn_drive_info drive_infos[]);
|
||||
|
||||
|
||||
/* ts A60823 */
|
||||
/* @since 0.2.2 */
|
||||
/** Maximum length+1 to expect with a persistent drive address string */
|
||||
#define BURN_DRIVE_ADR_LEN 1024
|
||||
|
||||
/* ts A70906 */
|
||||
/** Inquire the persistent address of the given drive.
|
||||
@param drive The drive to inquire.
|
||||
@param adr An application provided array of at least BURN_DRIVE_ADR_LEN
|
||||
characters size. The persistent address gets copied to it.
|
||||
@return >0 success , <=0 error (due to libburn internal problem)
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_drive_d_get_adr(struct burn_drive *drive, char adr[]);
|
||||
|
||||
/* A60823 */
|
||||
/** Inquire the persistent address of a drive via a given drive_info object.
|
||||
(Note: This is a legacy call.)
|
||||
@param drive_info The drive to inquire.Usually some &(drive_infos[driveno])
|
||||
@param adr An application provided array of at least BURN_DRIVE_ADR_LEN
|
||||
characters size. The persistent address gets copied to it.
|
||||
@return >0 success , <=0 error (due to libburn internal problem)
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_get_adr(struct burn_drive_info *drive_info, char adr[]);
|
||||
|
||||
@ -912,6 +936,7 @@ int burn_drive_get_adr(struct burn_drive_info *drive_info, char adr[]);
|
||||
/** Evaluate whether the given address would be a possible persistent drive
|
||||
address of libburn.
|
||||
@return 1 means yes, 0 means no
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_is_enumerable_adr(char *adr);
|
||||
|
||||
@ -924,6 +949,7 @@ int burn_drive_is_enumerable_adr(char *adr);
|
||||
@param adr An application provided array of at least BURN_DRIVE_ADR_LEN
|
||||
characters size. The persistent address gets copied to it.
|
||||
@return 1 = success , 0 = failure , -1 = severe error
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_convert_fs_adr(char *path, char adr[]);
|
||||
|
||||
@ -941,6 +967,7 @@ int burn_drive_convert_fs_adr(char *path, char adr[]);
|
||||
@param adr An application provided array of at least BURN_DRIVE_ADR_LEN
|
||||
characters size. The persistent address gets copied to it.
|
||||
@return 1 = success , 0 = failure , -1 = severe error
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_convert_scsi_adr(int bus_no, int host_no, int channel_no,
|
||||
int target_no, int lun_no, char adr[]);
|
||||
@ -951,6 +978,7 @@ int burn_drive_convert_scsi_adr(int bus_no, int host_no, int channel_no,
|
||||
drive address obtained via burn_drive_d_get_adr(). It is also supposed to
|
||||
succeed with any device file of a (possibly emulated) SCSI device.
|
||||
@return 1 = success , 0 = failure , -1 = severe error
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_obtain_scsi_adr(char *path, int *bus_no, int *host_no,
|
||||
int *channel_no, int *target_no, int *lun_no);
|
||||
@ -983,6 +1011,7 @@ void burn_drive_release(struct burn_drive *drive, int eject);
|
||||
@param drive The drive to release and leave locked.
|
||||
@param flag Bitfield for control purposes (unused yet, submit 0)
|
||||
@return 1 means success, <=0 means failure
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_drive_leave_locked(struct burn_drive *d, int flag);
|
||||
|
||||
@ -1003,6 +1032,7 @@ enum burn_disc_status burn_disc_get_status(struct burn_drive *drive);
|
||||
or BURN_DISC_UNSUITABLE. Thus marking media as writable which actually
|
||||
failed to declare themselves either blank or (partially) filled.
|
||||
@return 1 drive status has been set , 0 = unsuitable drive status
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_disc_pretend_blank(struct burn_drive *drive);
|
||||
|
||||
@ -1012,6 +1042,7 @@ int burn_disc_pretend_blank(struct burn_drive *drive);
|
||||
Sets the drive status to BURN_DISC_FULL if it is BURN_DISC_UNREADY
|
||||
or BURN_DISC_UNSUITABLE. Thus marking media as blankable which actually
|
||||
failed to declare themselves either blank or (partially) filled.
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_disc_pretend_full(struct burn_drive *drive);
|
||||
|
||||
@ -1022,6 +1053,7 @@ int burn_disc_pretend_full(struct burn_drive *drive);
|
||||
burn_drive_get_start_end_lba(). The drive must be grabbed for this call.
|
||||
@param drive The drive to query.
|
||||
@return 1=sucess, 0=no valid ATIP info read, -1 severe error
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_disc_read_atip(struct burn_drive *drive);
|
||||
|
||||
@ -1036,6 +1068,7 @@ int burn_disc_read_atip(struct burn_drive *drive);
|
||||
@param end_lba Returns the end lba value
|
||||
@param flag Bitfield for control purposes (unused yet, submit 0)
|
||||
@return 1 if lba values are valid , 0 if invalid
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_get_start_end_lba(struct burn_drive *drive,
|
||||
int *start_lba, int *end_lba, int flag);
|
||||
@ -1053,6 +1086,7 @@ int burn_drive_get_start_end_lba(struct burn_drive *drive,
|
||||
@param lba return value: start lba
|
||||
@param nwa return value: Next Writeable Address
|
||||
@return 1=nwa is valid , 0=nwa is not valid , -1=error
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_disc_track_lba_nwa(struct burn_drive *d, struct burn_write_opts *o,
|
||||
int trackno, int *lba, int *nwa);
|
||||
@ -1064,6 +1098,7 @@ int burn_disc_track_lba_nwa(struct burn_drive *d, struct burn_write_opts *o,
|
||||
@param d The drive to query.
|
||||
@param start_lba returns the start address of that track
|
||||
@return <= 0 : failure, 1 = ok
|
||||
@since 0.3.2
|
||||
*/
|
||||
int burn_disc_get_msc1(struct burn_drive *d, int *start_lba);
|
||||
|
||||
@ -1080,6 +1115,7 @@ int burn_disc_get_msc1(struct burn_drive *d, int *start_lba);
|
||||
@param d The drive to query.
|
||||
@param o If not NULL: write parameters to be set on drive before query
|
||||
@return number of most probably available free bytes
|
||||
@since 0.3.4
|
||||
*/
|
||||
off_t burn_disc_available_space(struct burn_drive *d,
|
||||
struct burn_write_opts *o);
|
||||
@ -1107,6 +1143,7 @@ off_t burn_disc_available_space(struct burn_drive *d,
|
||||
@param pno Profile Number. See also mmc5r03c.pdf, table 89
|
||||
@param name Profile Name (see above list, unknown profiles have empty name)
|
||||
@return 1 profile is valid, 0 no profile info available
|
||||
@since 0.3.0
|
||||
*/
|
||||
int burn_disc_get_profile(struct burn_drive *d, int *pno, char name[80]);
|
||||
|
||||
@ -1136,6 +1173,7 @@ struct burn_write_opts *burn_write_opts_new(struct burn_drive *drive);
|
||||
/** Inquires the drive associated with a burn_write_opts object.
|
||||
@param opts object to inquire
|
||||
@return pointer to drive
|
||||
@since 0.4.0
|
||||
*/
|
||||
struct burn_drive *burn_write_opts_get_drive(struct burn_write_opts *opts);
|
||||
|
||||
@ -1205,16 +1243,19 @@ void burn_disc_erase(struct burn_drive *drive, int fast);
|
||||
Acceptable types are: 0x00, 0x01, 0x10, 0x11, 0x13,
|
||||
0x15, 0x26, 0x30, 0x31.
|
||||
If bit7 is set, bit4 is set automatically.
|
||||
@since 0.3.0
|
||||
*/
|
||||
void burn_disc_format(struct burn_drive *drive, off_t size, int flag);
|
||||
|
||||
|
||||
/* ts A70112 */
|
||||
/* @since 0.3.0 */
|
||||
/** Possible formatting status values */
|
||||
#define BURN_FORMAT_IS_UNFORMATTED 1
|
||||
#define BURN_FORMAT_IS_FORMATTED 2
|
||||
#define BURN_FORMAT_IS_UNKNOWN 3
|
||||
|
||||
/* ts A70112 */
|
||||
/** Inquire the formatting status, the associated sizes and the number of
|
||||
available formats. The info is media specific and stems from MMC command
|
||||
23h READ FORMAT CAPACITY. See mmc5r03c.pdf 6.24 for background details.
|
||||
@ -1233,10 +1274,12 @@ void burn_disc_format(struct burn_drive *drive, off_t size, int flag);
|
||||
burn_disc_get_format_descr() to obtain such a format
|
||||
and eventually with burn_disc_format() to select one.
|
||||
@return 1 reply is valid , <=0 failure
|
||||
@since 0.3.0
|
||||
*/
|
||||
int burn_disc_get_formats(struct burn_drive *drive, int *status, off_t *size,
|
||||
unsigned *bl_sas, int *num_formats);
|
||||
|
||||
/* ts A70112 */
|
||||
/** Inquire parameters of an available media format.
|
||||
@param drive The drive with the disc to format.
|
||||
@param index The index of the format item. Beginning with 0 up to reply
|
||||
@ -1249,6 +1292,7 @@ int burn_disc_get_formats(struct burn_drive *drive, int *status, off_t *size,
|
||||
@param size The maximum size in bytes achievable with this format.
|
||||
@param tdp Type Dependent Parameter. See mmc5r03c.pdf.
|
||||
@return 1 reply is valid , <=0 failure
|
||||
@since 0.3.0
|
||||
*/
|
||||
int burn_disc_get_format_descr(struct burn_drive *drive, int index,
|
||||
int *type, off_t *size, unsigned *tdp);
|
||||
@ -1267,6 +1311,7 @@ void burn_disc_read(struct burn_drive *drive, const struct burn_read_opts *o);
|
||||
|
||||
|
||||
/* ts A70222 */
|
||||
/* @since 0.3.4 */
|
||||
/** The length of a rejection reasons string for burn_precheck_write() and
|
||||
burn_write_opts_auto_write_type() .
|
||||
*/
|
||||
@ -1282,6 +1327,7 @@ void burn_disc_read(struct burn_drive *drive, const struct burn_read_opts *o);
|
||||
@param reasons Eventually returns a list of rejection reason statements
|
||||
@param silent 1= do not issue error messages , 0= report problems
|
||||
@return 1 ok, -1= no recordable media detected, 0= other failure
|
||||
@since 0.3.4
|
||||
*/
|
||||
int burn_precheck_write(struct burn_write_opts *o, struct burn_disc *disc,
|
||||
char reasons[BURN_REASONS_LEN], int silent);
|
||||
@ -1315,6 +1361,7 @@ void burn_drive_cancel(struct burn_drive *drive);
|
||||
during write, a call to burn_drive_cancel() by the application thread.
|
||||
@param d The drive to inquire.
|
||||
@return 1=burn seems to have went well, 0=burn failed
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_wrote_well(struct burn_drive *d);
|
||||
|
||||
@ -1431,6 +1478,7 @@ void burn_track_define_data(struct burn_track *t, int offset, int tail,
|
||||
@param t The track to change
|
||||
@param swap_source_bytes 0=do not swap, 1=swap byte pairs
|
||||
@return 1=success , 0=unacceptable value
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_track_set_byte_swap(struct burn_track *t, int swap_source_bytes);
|
||||
|
||||
@ -1484,6 +1532,7 @@ enum burn_source_status burn_track_set_source(struct burn_track *t,
|
||||
@param t The track to change
|
||||
@param size The size to set
|
||||
@return 0=failure 1=sucess
|
||||
@since 0.3.4
|
||||
*/
|
||||
int burn_track_set_default_size(struct burn_track *t, off_t size);
|
||||
|
||||
@ -1543,6 +1592,7 @@ struct burn_source *burn_fd_source_new(int datafd, int subfd, off_t size);
|
||||
to be disposed by calling burn_source_free() for each.
|
||||
inp can be freed immediately, the returned fifo may be
|
||||
kept as handle for burn_fifo_inquire_status().
|
||||
@since 0.4.0
|
||||
*/
|
||||
struct burn_source *burn_fifo_source_new(struct burn_source *inp,
|
||||
int chunksize, int chunks, int flag);
|
||||
@ -1564,17 +1614,43 @@ struct burn_source *burn_fifo_source_new(struct burn_source *inp,
|
||||
5="abandoned" : consumption has ended prematurely
|
||||
6="ended" : consumption has ended without input error
|
||||
7="aborted" : consumption has ended after input error
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_fifo_inquire_status(struct burn_source *fifo, int *size,
|
||||
int *free_bytes, char **status_text);
|
||||
|
||||
|
||||
/* ts A80713 */
|
||||
/** Obtain a preview of the first input data of a fifo which was created
|
||||
by burn_fifo_source_new(). The data will later be delivered normally to
|
||||
the consumer track of the fifo.
|
||||
bufsize may not be larger than the fifo size (chunk_size * chunks).
|
||||
This call will succeed only if data consumption by the track has not
|
||||
started yet, i.e. best before the call to burn_disc_write().
|
||||
It will start the worker thread of the fifo with the expectable side
|
||||
effects on the external data source. Then it waits either until enough
|
||||
data have arrived or until it becomes clear that this will not happen.
|
||||
The call may be repeated with increased bufsize. It will always yield
|
||||
the bytes beginning from the first one in the fifo.
|
||||
@param fifo The fifo object to inquire
|
||||
@param buf Pointer to memory of at least bufsize bytes where to
|
||||
deliver the peeked data
|
||||
@param bufsize Number of bytes to peek from the start of the fifo data
|
||||
@param flag Bitfield for control purposes (unused yet, submit 0).
|
||||
@return <0 on severe error, 0 if not enough data, 1 if bufsize bytes read
|
||||
@since 0.5.0
|
||||
*/
|
||||
int burn_fifo_peek_data(struct burn_source *source, char *buf, int bufsize,
|
||||
int flag);
|
||||
|
||||
|
||||
/* ts A70328 */
|
||||
/** Sets a fixed track size after the data source object has already been
|
||||
created.
|
||||
@param t The track to operate on
|
||||
@param size the number of bytes to use as track size
|
||||
@return <=0 indicates failure , >0 success
|
||||
@since 0.3.6
|
||||
*/
|
||||
int burn_track_set_size(struct burn_track *t, off_t size);
|
||||
|
||||
@ -1587,7 +1663,12 @@ int burn_track_get_sectors(struct burn_track *);
|
||||
|
||||
/* ts A61101 */
|
||||
/** Tells how many source bytes have been read and how many data bytes have
|
||||
been written by the track during burn */
|
||||
been written by the track during burn.
|
||||
@param t The track to inquire
|
||||
@param read_bytes Number of bytes read from the track source
|
||||
@param written_bytes Number of bytes written to track
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_track_get_counters(struct burn_track *t,
|
||||
off_t *read_bytes, off_t *written_bytes);
|
||||
|
||||
@ -1632,6 +1713,7 @@ void burn_drive_set_speed(struct burn_drive *d, int read, int write);
|
||||
@param min_percent Minimum of desired buffer oscillation: 25 to 100
|
||||
@param max_percent Maximum of desired buffer oscillation: 25 to 100
|
||||
@return 1=success , 0=failure
|
||||
@since 0.3.8
|
||||
*/
|
||||
int burn_drive_set_buffer_waiting(struct burn_drive *d, int enable,
|
||||
int min_usec, int max_usec, int timeout_sec,
|
||||
@ -1669,6 +1751,7 @@ int burn_write_opts_set_write_type(struct burn_write_opts *opts,
|
||||
bit1= do not issue error messages via burn_msgs queue
|
||||
(is automatically set with bit0)
|
||||
@return Chosen write type. BURN_WRITE_NONE on failure.
|
||||
@since 0.3.2
|
||||
*/
|
||||
enum burn_write_types burn_write_opts_auto_write_type(
|
||||
struct burn_write_opts *opts, struct burn_disc *disc,
|
||||
@ -1733,6 +1816,7 @@ void burn_write_opts_set_mediacatalog(struct burn_write_opts *opts, unsigned cha
|
||||
being the last one and thus creating a BURN_DISC_APPENDABLE media.
|
||||
@param opts The option object to be manipulated
|
||||
@param multi 1=media will be appendable, 0=media will be closed (default)
|
||||
@since 0.2.6
|
||||
*/
|
||||
void burn_write_opts_set_multi(struct burn_write_opts *opts, int multi);
|
||||
|
||||
@ -1749,6 +1833,7 @@ void burn_write_opts_set_multi(struct burn_write_opts *opts, int multi);
|
||||
.start_range_low , .start_range_high .
|
||||
@param opts The write opts to change
|
||||
@param value The address in bytes (-1 = start at default address)
|
||||
@since 0.3.0
|
||||
*/
|
||||
void burn_write_opts_set_start_byte(struct burn_write_opts *opts, off_t value);
|
||||
|
||||
@ -1761,6 +1846,7 @@ void burn_write_opts_set_start_byte(struct burn_write_opts *opts, off_t value);
|
||||
by the last track of the last session.
|
||||
@param opts The write opts to change
|
||||
@param fill_up_media If 1 : fill up by last track, if 0 = do not fill up
|
||||
@since 0.3.4
|
||||
*/
|
||||
void burn_write_opts_set_fillup(struct burn_write_opts *opts,
|
||||
int fill_up_media);
|
||||
@ -1772,6 +1858,7 @@ void burn_write_opts_set_fillup(struct burn_write_opts *opts,
|
||||
- the check whether the media profile supports simulated burning
|
||||
@param opts The write opts to change
|
||||
@param use_force 1=ignore above checks, 0=refuse work on failed check
|
||||
@since 0.3.4
|
||||
*/
|
||||
void burn_write_opts_set_force(struct burn_write_opts *opts, int use_force);
|
||||
|
||||
@ -1782,9 +1869,9 @@ void burn_write_opts_set_force(struct burn_write_opts *opts, int use_force);
|
||||
slowdown to half nominal speed. But if it speeds up writing then it also
|
||||
disables error management and correction. Weigh your priorities.
|
||||
This only affects the write operations of burn_disc_write().
|
||||
@since 0.4.6
|
||||
@param opts The write opts to change
|
||||
@param value 0=use 2Ah WRITE10, 1=use AAh WRITE12 with Streaming bit
|
||||
@since 0.4.6
|
||||
*/
|
||||
void burn_write_opts_set_stream_recording(struct burn_write_opts *opts,
|
||||
int value);
|
||||
@ -1860,6 +1947,7 @@ int burn_drive_get_write_speed(struct burn_drive *d);
|
||||
again by call burn_drive_grab() and again by call burn_disc_read_atip().
|
||||
@param d Drive to query
|
||||
@return Minimum write speed in K/s
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_drive_get_min_write_speed(struct burn_drive *d);
|
||||
|
||||
@ -1882,6 +1970,7 @@ int burn_drive_get_read_speed(struct burn_drive *d);
|
||||
@param d Drive to query
|
||||
@param speed_list The copy. If empty, *speed_list gets returned as NULL.
|
||||
@return 1=success , 0=list empty , <0 severe error
|
||||
@since 0.3.0
|
||||
*/
|
||||
int burn_drive_get_speedlist(struct burn_drive *d,
|
||||
struct burn_speed_descriptor **speed_list);
|
||||
@ -1901,6 +1990,7 @@ int burn_drive_get_speedlist(struct burn_drive *d,
|
||||
bit1= look for any source type (else look for source==2 first
|
||||
and for any other source type only with CD media)
|
||||
@return >0 indicates a valid best_descr, 0 = no valid best_descr
|
||||
@since 0.3.8
|
||||
*/
|
||||
int burn_drive_get_best_speed(struct burn_drive *d, int speed_goal,
|
||||
struct burn_speed_descriptor **best_descr, int flag);
|
||||
@ -1911,11 +2001,13 @@ int burn_drive_get_best_speed(struct burn_drive *d, int speed_goal,
|
||||
burn_drive_get_speedlist().
|
||||
@param speed_list The list copy. *speed_list gets set to NULL.
|
||||
@return 1=list disposed , 0= *speedlist was already NULL
|
||||
@since 0.3.0
|
||||
*/
|
||||
int burn_drive_free_speedlist(struct burn_speed_descriptor **speed_list);
|
||||
|
||||
|
||||
/* ts A70203 */
|
||||
/* @since 0.3.2 */
|
||||
/** The reply structure for burn_disc_get_multi_caps()
|
||||
*/
|
||||
struct burn_multi_caps {
|
||||
@ -1993,7 +2085,8 @@ struct burn_multi_caps {
|
||||
/** Wether the current profile indicates CD media. 1=yes, 0=no */
|
||||
int current_is_cd_profile;
|
||||
|
||||
/* ts A70528, added to version 0.3.7 */
|
||||
/* ts A70528 */
|
||||
/* @since 0.3.8 */
|
||||
/** Wether the current profile is able to perform simulated write */
|
||||
int might_simulate;
|
||||
};
|
||||
@ -2010,6 +2103,7 @@ struct burn_multi_caps {
|
||||
@param caps returns the info structure
|
||||
@param flag Bitfield for control purposes (unused yet, submit 0)
|
||||
@return < 0 : error , 0 : writing seems impossible , 1 : writing possible
|
||||
@since 0.3.2
|
||||
*/
|
||||
int burn_disc_get_multi_caps(struct burn_drive *d, enum burn_write_types wt,
|
||||
struct burn_multi_caps **caps, int flag);
|
||||
@ -2018,6 +2112,7 @@ int burn_disc_get_multi_caps(struct burn_drive *d, enum burn_write_types wt,
|
||||
burn_disc_get_multi_caps(). The pointer *caps gets set to NULL.
|
||||
@param caps the info structure to dispose (note: pointer to pointer)
|
||||
@return 0 : *caps was already NULL, 1 : memory object was disposed
|
||||
@since 0.3.2
|
||||
*/
|
||||
int burn_disc_free_multi_caps(struct burn_multi_caps **caps);
|
||||
|
||||
@ -2080,6 +2175,7 @@ void burn_version(int *major, int *minor, int *micro);
|
||||
|
||||
|
||||
/* ts A80129 */
|
||||
/* @since 0.4.4 */
|
||||
/** These three release version numbers tell the revision of this header file
|
||||
and of the API it describes. They are memorized by applications at build
|
||||
time.
|
||||
@ -2097,8 +2193,8 @@ void burn_version(int *major, int *minor, int *micro);
|
||||
|
||||
*/
|
||||
#define burn_header_version_major 0
|
||||
#define burn_header_version_minor 4
|
||||
#define burn_header_version_micro 8
|
||||
#define burn_header_version_minor 5
|
||||
#define burn_header_version_micro 4
|
||||
/** Note:
|
||||
Above version numbers are also recorded in configure.ac because libtool
|
||||
wants them as parameters at build time.
|
||||
@ -2160,12 +2256,13 @@ These two advises are mutually exclusive.
|
||||
to stderr. Default: "FATAL".
|
||||
@param print_id A text prefix to be printed before the message.
|
||||
@return >0 for success, <=0 for error
|
||||
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_msgs_set_severities(char *queue_severity,
|
||||
char *print_severity, char *print_id);
|
||||
|
||||
/* ts A60924 : ticket 74 */
|
||||
/* @since 0.2.6 */
|
||||
#define BURN_MSGS_MESSAGE_LEN 4096
|
||||
|
||||
/** Obtain the oldest pending libburn message from the queue which has at
|
||||
@ -2183,6 +2280,7 @@ int burn_msgs_set_severities(char *queue_severity,
|
||||
@param severity Will become the severity related to the message and
|
||||
should provide at least 80 bytes.
|
||||
@return 1 if a matching item was found, 0 if not, <0 for severe errors
|
||||
@since 0.2.6
|
||||
*/
|
||||
int burn_msgs_obtain(char *minimum_severity,
|
||||
int *error_code, char msg_text[], int *os_errno,
|
||||
@ -2205,6 +2303,7 @@ int burn_msgs_obtain(char *minimum_severity,
|
||||
Submit NULL if the message is not specific to a
|
||||
particular drive object.
|
||||
@return 1 if message was delivered, <=0 if failure
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_msgs_submit(int error_code, char msg_text[], int os_errno,
|
||||
char severity[], struct burn_drive *d);
|
||||
@ -2217,6 +2316,7 @@ int burn_msgs_submit(int error_code, char msg_text[], int os_errno,
|
||||
@param severity_number The rank number: the higher, the more severe.
|
||||
@param flag Bitfield for control purposes (unused yet, submit 0)
|
||||
@return >0 success, <=0 failure
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_text_to_sev(char *severity_name, int *severity_number, int flag);
|
||||
|
||||
@ -2227,6 +2327,7 @@ int burn_text_to_sev(char *severity_name, int *severity_number, int flag);
|
||||
@param severity_number The rank number: the higher, the more severe.
|
||||
@param severity_name A name as with burn_msgs_submit(), e.g. "SORRY".
|
||||
@param flag Bitfield for control purposes (unused yet, submit 0)
|
||||
@since 0.4.4
|
||||
*/
|
||||
int burn_sev_to_text(int severity_number, char **severity_name, int flag);
|
||||
|
||||
@ -2238,11 +2339,13 @@ int burn_sev_to_text(int severity_number, char **severity_name, int flag);
|
||||
See also: libisofs, API function iso_get_messenger().
|
||||
@param messenger The foreign but compatible message handle.
|
||||
@return 1 : success, <=0 : failure
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_set_messenger(void *messenger);
|
||||
|
||||
|
||||
/* ts A61002 */
|
||||
/* @since 0.2.6 */
|
||||
/** The prototype of a handler function suitable for burn_set_abort_handling().
|
||||
Such a function has to return -2 if it does not want the process to
|
||||
exit with value 1.
|
||||
@ -2261,6 +2364,7 @@ typedef int (*burn_abort_handler_t)(void *handle, int signum, int flag);
|
||||
Arguments (text, NULL, 0) activate the builtin abort handler. It will
|
||||
eventually call burn_abort() and then perform exit(1). If text is not NULL
|
||||
then it is used as prefix for pacifier messages of burn_abort_pacifier().
|
||||
@since 0.2.6
|
||||
*/
|
||||
void burn_set_signal_handling(void *handle, burn_abort_handler_t handler,
|
||||
int mode);
|
||||
@ -2293,6 +2397,7 @@ void burn_set_signal_handling(void *handle, burn_abort_handler_t handler,
|
||||
@param flag Bitfield for control purposes:
|
||||
bit0 = flush the drive buffer after eventual writing
|
||||
@return 1=sucessful , <=0 : number of transfered bytes * -1
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_random_access_write(struct burn_drive *d, off_t byte_address,
|
||||
char *data, off_t data_count, int flag);
|
||||
@ -2316,7 +2421,10 @@ int burn_random_access_write(struct burn_drive *d, off_t byte_address,
|
||||
@param flag Bitfield for control purposes:
|
||||
bit0= - reserved -
|
||||
bit1= do not submit error message if read error
|
||||
bit2= on error do not try to read a second time
|
||||
with single block steps. @since 0.5.2
|
||||
@return 1=sucessful , <=0 an error occured
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_read_data(struct burn_drive *d, off_t byte_address,
|
||||
char data[], off_t data_size, off_t *data_count, int flag);
|
||||
@ -2330,6 +2438,7 @@ int burn_read_data(struct burn_drive *d, off_t byte_address,
|
||||
1= real MMC drive
|
||||
2= stdio-drive, random access, read-write
|
||||
3= stdio-drive, sequential, write-only
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_drive_get_drive_role(struct burn_drive *d);
|
||||
|
||||
@ -2356,6 +2465,7 @@ int burn_drive_get_drive_role(struct burn_drive *d);
|
||||
prefix "stdio:".
|
||||
@return 1= adr2 leads to d1 , 0= adr2 seems not to lead to d1,
|
||||
-1 = adr2 is bad
|
||||
@since 0.4.0
|
||||
*/
|
||||
int burn_drive_equals_adr(struct burn_drive *d1, char *adr2, int drive_role2);
|
||||
|
||||
|
@ -432,6 +432,8 @@ Range "scdbackup" : 0x00020000 to 0x0002ffff
|
||||
0x00020007 (NOTE,HIGH) = Closed O_EXCL scsi siblings
|
||||
0x00020008 (SORRY,HIGH) = Device busy. Failed to fcntl-lock
|
||||
0x00020009 (SORRY,HIGH) = Neither stdio-path nor its directory exist
|
||||
0x0002000a (FAILURE,HIGH) = Cannot accept '...' as SG_IO CDROM drive
|
||||
0x0002000b (FAILURE,HIGH) = File object '...' not found
|
||||
|
||||
General library operations:
|
||||
|
||||
@ -524,6 +526,11 @@ Range "scdbackup" : 0x00020000 to 0x0002ffff
|
||||
0x00020157 (FATAL,HIGH) = burn_source is not a fifo object
|
||||
0x00020158 (DEBUG,LOW) = Reporting thread disposal precautions
|
||||
0x00020159 (DEBUG,HIGH) = TOC Format 0 returns inconsistent data
|
||||
0x0002015a (NOTE,HIGH) = Could not examine busy device
|
||||
0x0002015b (HINT,HIGH) = Busy '...' seems to be a hard disk, as '...1' exists
|
||||
0x0002015c (FAILURE,HIGH) = Fifo size is smaller than desired peek buffer
|
||||
0x0002015d (FAILURE,HIGH) = Fifo input ended short of desired peek buffer size
|
||||
0x0002015e (FATAL,HIGH) = Fifo is already under consumption when peeking
|
||||
|
||||
libdax_audioxtr:
|
||||
0x00020200 (SORRY,HIGH) = Cannot open audio source file
|
||||
|
@ -62,7 +62,7 @@ extern struct libdax_msgs *libdax_messenger;
|
||||
/* ts A80410 : <<< Dangerous experiment: Pretend that DVD-RAM is BD-RE
|
||||
# define Libburn_dvd_ram_as_bd_rE yes
|
||||
*/
|
||||
/* ts A80509 : <<< Experiment: pretend that DVD-COM and CD-ROM are other media
|
||||
/* ts A80509 : <<< Experiment: pretend that DVD-ROM and CD-ROM are other media
|
||||
like BD-ROM (0x40), BD-R seq (0x41), BD-R random (0x42)
|
||||
# define Libburn_rom_as_profilE 0x40
|
||||
*/
|
||||
@ -773,11 +773,24 @@ int mmc_write(struct burn_drive *d, int start, struct buffer *buf)
|
||||
|
||||
/* >>> make this scsi_notify_error() when liberated */
|
||||
if (c.sense[2]!=0) {
|
||||
|
||||
#ifdef NIX
|
||||
char msg[160];
|
||||
sprintf(msg,
|
||||
"SCSI error on write(%d,%d): key=%X asc=%2.2Xh ascq=%2.2Xh",
|
||||
start, len,
|
||||
c.sense[2],c.sense[12],c.sense[13]);
|
||||
#else /* NIX */
|
||||
char msg[256];
|
||||
int key, asc, ascq;
|
||||
|
||||
sprintf(msg, "SCSI error on write(%d,%d): ",
|
||||
start, len);
|
||||
scsi_error_msg(d, c.sense, 14, msg + strlen(msg),
|
||||
&key, &asc, &ascq);
|
||||
|
||||
#endif /* !NIX */
|
||||
|
||||
libdax_msgs_submit(libdax_messenger, d->global_index,
|
||||
0x0002011d,
|
||||
LIBDAX_MSGS_SEV_FATAL, LIBDAX_MSGS_PRIO_HIGH,
|
||||
@ -1293,6 +1306,10 @@ static int mmc_read_toc_al(struct burn_drive *d, int *alloc_len)
|
||||
if (d->status == BURN_DISC_UNREADY)
|
||||
d->status = BURN_DISC_FULL;
|
||||
toc_find_modes(d);
|
||||
|
||||
/* A80808 */
|
||||
burn_disc_cd_toc_extensions(d->disc, 0);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -1920,8 +1937,9 @@ int mmc_set_streaming(struct burn_drive *d,
|
||||
struct buffer buf;
|
||||
struct command c;
|
||||
int b, eff_end_lba;
|
||||
char msg[160];
|
||||
char msg[256];
|
||||
unsigned char *pd;
|
||||
int key, asc, ascq;
|
||||
|
||||
if (mmc_function_spy(d, "mmc_set_streaming") <= 0)
|
||||
return 0;
|
||||
@ -1984,6 +2002,8 @@ int mmc_set_streaming(struct burn_drive *d,
|
||||
d->issue_command(d, &c);
|
||||
if (c.error) {
|
||||
if (c.sense[2]!=0 && !d->silent_on_scsi_error) {
|
||||
|
||||
#ifdef NIX
|
||||
sprintf(msg,
|
||||
"SCSI error on set_streaming(%d): key=%X asc=%2.2Xh ascq=%2.2Xh",
|
||||
w_speed,
|
||||
@ -1993,6 +2013,15 @@ int mmc_set_streaming(struct burn_drive *d,
|
||||
0x00020124,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_HIGH,
|
||||
msg, 0, 0);
|
||||
#else /* NIX */
|
||||
|
||||
sprintf(msg,
|
||||
"SCSI error on set_streaming(%d): ", w_speed);
|
||||
scsi_error_msg(d, c.sense, 14, msg + strlen(msg),
|
||||
&key, &asc, &ascq);
|
||||
|
||||
#endif /* !NIX */
|
||||
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -2694,7 +2723,8 @@ int mmc_format_unit(struct burn_drive *d, off_t size, int flag)
|
||||
int index, format_sub_type = 0, format_00_index, size_mode;
|
||||
int accept_count = 0;
|
||||
off_t num_of_blocks = 0, diff, format_size, i_size, format_00_max_size;
|
||||
char msg[160],descr[80];
|
||||
char msg[256],descr[80];
|
||||
int key, asc, ascq;
|
||||
int full_format_type = 0x00; /* Full Format (or 0x10 for DVD-RW ?) */
|
||||
|
||||
if (mmc_function_spy(d, "mmc_format_unit") <= 0)
|
||||
@ -3096,6 +3126,8 @@ unsuitable_media:;
|
||||
d->issue_command(d, &c);
|
||||
if (c.error && !tolerate_failure) {
|
||||
if (c.sense[2]!=0) {
|
||||
|
||||
#ifdef NIX
|
||||
sprintf(msg,
|
||||
"SCSI error on format_unit(%s): key=%X asc=%2.2Xh ascq=%2.2Xh",
|
||||
descr,
|
||||
@ -3104,6 +3136,13 @@ unsuitable_media:;
|
||||
0x00020122,
|
||||
LIBDAX_MSGS_SEV_FATAL, LIBDAX_MSGS_PRIO_HIGH,
|
||||
msg, 0, 0);
|
||||
#else /* NIX */
|
||||
sprintf(msg, "SCSI error on format_unit(%s): ", descr);
|
||||
scsi_error_msg(d, c.sense, 14, msg + strlen(msg),
|
||||
&key, &asc, &ascq);
|
||||
|
||||
#endif /* !NIX */
|
||||
|
||||
}
|
||||
return 0;
|
||||
} else if ((!c.error) && (format_type == 0x13 || format_type == 0x15))
|
||||
@ -3405,11 +3444,24 @@ int mmc_read_10(struct burn_drive *d, int start,int amount, struct buffer *buf)
|
||||
c.dir = FROM_DRIVE;
|
||||
d->issue_command(d, &c);
|
||||
if (c.error) {
|
||||
|
||||
#ifdef NIX
|
||||
char msg[160];
|
||||
|
||||
sprintf(msg,
|
||||
"SCSI error on read_10(%d,%d): key=%X asc=%2.2Xh ascq=%2.2Xh",
|
||||
start, amount,
|
||||
c.sense[2],c.sense[12],c.sense[13]);
|
||||
#else /* NIX */
|
||||
char msg[256];
|
||||
int key, asc, ascq;
|
||||
|
||||
sprintf(msg, "SCSI error on read_10(%d,%d): ", start, amount);
|
||||
scsi_error_msg(d, c.sense, 14, msg + strlen(msg),
|
||||
&key, &asc, &ascq);
|
||||
|
||||
#endif /* !NIX */
|
||||
|
||||
if(!d->silent_on_scsi_error)
|
||||
libdax_msgs_submit(libdax_messenger, d->global_index,
|
||||
0x00020144,
|
||||
|
@ -51,11 +51,17 @@ SIGKILL, SIGCHLD, SIGSTOP, SIGURG, SIGWINCH
|
||||
#define BURN_OS_TRANSPORT_BUFFER_SIZE 65536
|
||||
|
||||
|
||||
/* To hold the index number of the most recently delivered address from
|
||||
/* To hold the position of the most recently delivered address from
|
||||
device enumeration.
|
||||
*/
|
||||
struct burn_drive_enumerator_struct {
|
||||
int pos;
|
||||
int info_count;
|
||||
char **info_list;
|
||||
};
|
||||
|
||||
#define BURN_OS_DEFINE_DRIVE_ENUMERATOR_T \
|
||||
typedef int burn_drive_enumerator_t;
|
||||
typedef struct burn_drive_enumerator_struct burn_drive_enumerator_t;
|
||||
|
||||
|
||||
/* Parameters for sibling list. See sibling_fds, sibling_fnames */
|
||||
|
@ -323,7 +323,7 @@ int burn_read_data(struct burn_drive *d, off_t byte_address,
|
||||
int alignment = 2048, start, upto, chunksize = 1, err, cpy_size, i;
|
||||
int sose_mem = 0, fd = -1, ret;
|
||||
char msg[81], *wpt;
|
||||
struct buffer buf;
|
||||
struct buffer buf, *buffer_mem = d->buffer;
|
||||
|
||||
/*
|
||||
#define Libburn_read_data_adr_logginG 1
|
||||
@ -443,7 +443,8 @@ int burn_read_data(struct burn_drive *d, off_t byte_address,
|
||||
d->silent_on_scsi_error = sose_mem;
|
||||
if (err == BE_CANCELLED) {
|
||||
/* Try to read a smaller part of the chunk */
|
||||
for (i = 0; i < chunksize - 1; i++) {
|
||||
if(!(flag & 4))
|
||||
for (i = 0; i < chunksize - 1; i++) {
|
||||
if (flag & 2)
|
||||
d->silent_on_scsi_error = 1;
|
||||
if (d->drive_role == 1) {
|
||||
@ -484,7 +485,7 @@ ex:;
|
||||
if (fd != -1)
|
||||
close(fd);
|
||||
*/
|
||||
d->buffer = NULL;
|
||||
d->buffer = buffer_mem;
|
||||
d->busy = BURN_DRIVE_IDLE;
|
||||
return ret;
|
||||
}
|
||||
|
@ -260,6 +260,37 @@ static void sg_select_device_family(void)
|
||||
}
|
||||
|
||||
|
||||
/* ts A80701 */
|
||||
/* This cares for the case that no /dev/srNN but only /dev/scdNN exists.
|
||||
A theoretical case which has its complement in SuSE 10.2 having
|
||||
/dev/sr but not /dev/scd.
|
||||
*/
|
||||
static int sg_exchange_scd_for_sr(char *fname, int flag)
|
||||
{
|
||||
struct stat stbuf;
|
||||
char scd[17], msg[160];
|
||||
|
||||
if (burn_sg_use_family != 0 || strncmp(fname, "/dev/sr", 7)!=0 ||
|
||||
strlen(fname)>9 || strlen(fname)<8)
|
||||
return 2;
|
||||
if (fname[7] < '0' || fname[7] > '9')
|
||||
return 2;
|
||||
if (fname [8] != 0 && (fname[7] < '0' || fname[7] > '9'))
|
||||
return 2;
|
||||
if (stat(fname, &stbuf) != -1)
|
||||
return 2;
|
||||
strcpy(scd, "/dev/scd");
|
||||
strcpy(scd + 8, fname + 7);
|
||||
if (stat(scd, &stbuf) == -1)
|
||||
return 2;
|
||||
sprintf(msg, "%s substitutes for non-existent %s", scd, fname);
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x00000002,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_HIGH, msg, 0, 0);
|
||||
strcpy(fname, scd);
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
static int sgio_test(int fd)
|
||||
{
|
||||
unsigned char test_ops[] = { 0, 0, 0, 0, 0, 0 };
|
||||
@ -279,6 +310,33 @@ static int sgio_test(int fd)
|
||||
static int sg_handle_busy_device(char *fname, int os_errno)
|
||||
{
|
||||
char msg[4096];
|
||||
struct stat stbuf;
|
||||
int looks_like_hd= 0, fd, ret;
|
||||
|
||||
/* ts A80713 :
|
||||
check existence of /dev/hdX1 as hint for hard disk rather than CD
|
||||
Hint by Giulio Orsero: check /proc/ide/hdX/media for "disk"
|
||||
*/
|
||||
if (strncmp(fname, "/dev/hd", 7)==0) {
|
||||
sprintf(msg, "%s1", fname);
|
||||
if (stat(msg, &stbuf) != -1)
|
||||
looks_like_hd= 1;
|
||||
sprintf(msg, "/proc/ide/hd%c/media", fname[7]);
|
||||
fd = open(msg, O_RDONLY);
|
||||
if (fd != -1) {
|
||||
ret = read(fd, msg, 10);
|
||||
if (ret < 0)
|
||||
ret = 0;
|
||||
msg[ret]= 0;
|
||||
close(fd);
|
||||
if (strncmp(msg, "disk\n", 5) == 0 ||
|
||||
strcmp(msg, "disk") == 0)
|
||||
looks_like_hd= 2;
|
||||
else if (strncmp(msg, "cdrom\n", 6) == 0 ||
|
||||
strcmp(msg, "cdrom") == 0)
|
||||
looks_like_hd= 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* ts A60814 : i saw no way to do this more nicely */
|
||||
if (burn_sg_open_abort_busy) {
|
||||
@ -292,10 +350,26 @@ static int sg_handle_busy_device(char *fname, int os_errno)
|
||||
}
|
||||
|
||||
/* ts A60924 : now reporting to libdax_msgs */
|
||||
sprintf(msg, "Cannot open busy device '%s'", fname);
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x00020001,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_LOW,
|
||||
msg, os_errno, 0);
|
||||
if (looks_like_hd == 2) { /* is surely hard disk */
|
||||
;
|
||||
} else if (looks_like_hd) {
|
||||
sprintf(msg, "Could not examine busy device '%s'", fname);
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x0002015a,
|
||||
LIBDAX_MSGS_SEV_NOTE, LIBDAX_MSGS_PRIO_LOW,
|
||||
msg, os_errno, 0);
|
||||
sprintf(msg,
|
||||
"Busy '%s' seems to be a hard disk, as '%s1' exists. But better check.",
|
||||
fname, fname);
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x0002015b,
|
||||
LIBDAX_MSGS_SEV_HINT, LIBDAX_MSGS_PRIO_LOW,
|
||||
msg, 0, 0);
|
||||
|
||||
} else {
|
||||
sprintf(msg, "Cannot open busy device '%s'", fname);
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x00020001,
|
||||
LIBDAX_MSGS_SEV_SORRY, LIBDAX_MSGS_PRIO_LOW,
|
||||
msg, os_errno, 0);
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -570,12 +644,193 @@ failed:;
|
||||
}
|
||||
|
||||
|
||||
#define Libburn_drive_new_deaL 1
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
|
||||
/* ts A80731 */
|
||||
static int is_ata_drive(char *fname)
|
||||
{
|
||||
int fd;
|
||||
struct hd_driveid tm;
|
||||
|
||||
fd = sg_open_drive_fd(fname, 1);
|
||||
if (fd == -1) {
|
||||
if (linux_ata_enumerate_verbous)
|
||||
fprintf(stderr,"open failed, errno=%d '%s'\n",
|
||||
errno, strerror(errno));
|
||||
return 0;
|
||||
}
|
||||
|
||||
memset(&tm, 0, sizeof(tm));
|
||||
ioctl(fd, HDIO_GET_IDENTITY, &tm);
|
||||
|
||||
/* not atapi */
|
||||
if (!(tm.config & 0x8000) || (tm.config & 0x4000)) {
|
||||
if (linux_ata_enumerate_verbous)
|
||||
fprintf(stderr, "not marked as ATAPI\n");
|
||||
sg_close_drive_fd(fname, -1, &fd, 0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* if SG_IO fails on an atapi device, we should stop trying to
|
||||
use hd* devices */
|
||||
if (sgio_test(fd) == -1) {
|
||||
if (linux_ata_enumerate_verbous)
|
||||
fprintf(stderr,
|
||||
"FATAL: sgio_test() failed: errno=%d '%s'\n",
|
||||
errno, strerror(errno));
|
||||
sg_close_drive_fd(fname, -1, &fd, 0);
|
||||
return 0;
|
||||
}
|
||||
if (sg_close_drive_fd(fname, -1, &fd, 1) <= 0) {
|
||||
if (linux_ata_enumerate_verbous)
|
||||
fprintf(stderr,
|
||||
"cannot close properly, errno=%d '%s'\n",
|
||||
errno, strerror(errno));
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
static int is_scsi_drive(char *fname, int *bus_no, int *host_no,
|
||||
int *channel_no, int *target_no, int *lun_no)
|
||||
{
|
||||
int fd, sid_ret = 0, ret;
|
||||
struct sg_scsi_id sid;
|
||||
int sibling_fds[BURN_OS_SG_MAX_SIBLINGS], sibling_count= 0;
|
||||
char sibling_fnames[BURN_OS_SG_MAX_SIBLINGS][BURN_OS_SG_MAX_NAMELEN];
|
||||
|
||||
fd = sg_open_drive_fd(fname, 1);
|
||||
if (fd == -1) {
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr, "open failed, errno=%d '%s'\n",
|
||||
errno, strerror(errno));
|
||||
return 0;
|
||||
}
|
||||
|
||||
sid_ret = ioctl(fd, SG_GET_SCSI_ID, &sid);
|
||||
if (sid_ret == -1) {
|
||||
sid.scsi_id = -1; /* mark SCSI address as invalid */
|
||||
if(linux_sg_enumerate_debug)
|
||||
fprintf(stderr,
|
||||
"ioctl(SG_GET_SCSI_ID) failed, errno=%d '%s' , ",
|
||||
errno, strerror(errno));
|
||||
|
||||
if (sgio_test(fd) == -1) {
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr,
|
||||
"FATAL: sgio_test() failed: errno=%d '%s'",
|
||||
errno, strerror(errno));
|
||||
|
||||
sg_close_drive_fd(fname, -1, &fd, 0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef CDROM_DRIVE_STATUS
|
||||
/* http://developer.osdl.org/dev/robustmutexes/
|
||||
src/fusyn.hg/Documentation/ioctl/cdrom.txt */
|
||||
sid_ret = ioctl(fd, CDROM_DRIVE_STATUS, 0);
|
||||
if(linux_sg_enumerate_debug)
|
||||
fprintf(stderr,
|
||||
"ioctl(CDROM_DRIVE_STATUS) = %d , ",
|
||||
sid_ret);
|
||||
if (sid_ret != -1 && sid_ret != CDS_NO_INFO)
|
||||
sid.scsi_type = TYPE_ROM;
|
||||
else
|
||||
sid_ret = -1;
|
||||
#endif /* CDROM_DRIVE_STATUS */
|
||||
|
||||
}
|
||||
|
||||
#ifdef SCSI_IOCTL_GET_BUS_NUMBER
|
||||
/* Hearsay A61005 */
|
||||
if (ioctl(fd, SCSI_IOCTL_GET_BUS_NUMBER, bus_no) == -1)
|
||||
*bus_no = -1;
|
||||
#endif
|
||||
|
||||
if (sg_close_drive_fd(fname, -1, &fd,
|
||||
sid.scsi_type == TYPE_ROM ) <= 0) {
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr,
|
||||
"cannot close properly, errno=%d '%s'\n",
|
||||
errno, strerror(errno));
|
||||
return 0;
|
||||
}
|
||||
if ( (sid_ret == -1 || sid.scsi_type != TYPE_ROM)
|
||||
&& !linux_sg_accept_any_type) {
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr, "sid.scsi_type = %d (!= TYPE_ROM)\n",
|
||||
sid.scsi_type);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (sid_ret == -1 || sid.scsi_id < 0) {
|
||||
/* ts A61211 : employ a more general ioctl */
|
||||
ret = sg_obtain_scsi_adr(fname, bus_no, host_no,
|
||||
channel_no, target_no, lun_no);
|
||||
if (ret>0) {
|
||||
sid.host_no = *host_no;
|
||||
sid.channel = *channel_no;
|
||||
sid.scsi_id = *target_no;
|
||||
sid.lun = *lun_no;
|
||||
} else {
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr,
|
||||
"sg_obtain_scsi_adr() failed\n");
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* ts A60927 : trying to do locking with growisofs */
|
||||
if(burn_sg_open_o_excl>1) {
|
||||
ret = sg_open_scsi_siblings(
|
||||
fname, -1, sibling_fds, sibling_fnames,
|
||||
&sibling_count,
|
||||
sid.host_no, sid.channel,
|
||||
sid.scsi_id, sid.lun);
|
||||
if (ret<=0) {
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr, "cannot lock siblings\n");
|
||||
sg_handle_busy_device(fname, 0);
|
||||
return 0;
|
||||
}
|
||||
/* the final occupation will be done in sg_grab() */
|
||||
sg_release_siblings(sibling_fds, sibling_fnames,
|
||||
&sibling_count);
|
||||
}
|
||||
#ifdef SCSI_IOCTL_GET_BUS_NUMBER
|
||||
if(*bus_no == -1)
|
||||
*bus_no = 1000 * (sid.host_no + 1) + sid.channel;
|
||||
#else
|
||||
*bus_no = sid.host_no;
|
||||
#endif
|
||||
*host_no= sid.host_no;
|
||||
*channel_no= sid.channel;
|
||||
*target_no= sid.scsi_id;
|
||||
*lun_no= sid.lun;
|
||||
return 1;
|
||||
}
|
||||
|
||||
#endif /* Libburn_drive_new_deaL */
|
||||
|
||||
|
||||
/** Speciality of Linux: detect non-SCSI ATAPI (EIDE) which will from
|
||||
then on used used via generic SCSI as is done with (emulated) SCSI drives */
|
||||
static void ata_enumerate(void)
|
||||
{
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
|
||||
int ret;
|
||||
|
||||
#else
|
||||
struct hd_driveid tm;
|
||||
int i, fd;
|
||||
int fd;
|
||||
#endif
|
||||
|
||||
int i;
|
||||
char fname[10];
|
||||
|
||||
if (linux_ata_enumerate_verbous)
|
||||
@ -596,6 +851,17 @@ static void ata_enumerate(void)
|
||||
fprintf(stderr, "not in whitelist\n");
|
||||
continue;
|
||||
}
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
|
||||
ret = is_ata_drive(fname);
|
||||
if (ret < 0)
|
||||
break;
|
||||
if (ret == 0)
|
||||
continue;
|
||||
|
||||
#else /* Libburn_drive_new_deaL */
|
||||
|
||||
fd = sg_open_drive_fd(fname, 1);
|
||||
if (fd == -1) {
|
||||
if (linux_ata_enumerate_verbous)
|
||||
@ -632,6 +898,10 @@ static void ata_enumerate(void)
|
||||
errno, strerror(errno));
|
||||
continue;
|
||||
}
|
||||
|
||||
#endif /* Libburn_drive_new_deaL */
|
||||
|
||||
|
||||
if (linux_ata_enumerate_verbous)
|
||||
fprintf(stderr, "accepting as drive without SCSI address\n");
|
||||
enumerate_common(fname, -1, -1, -1, -1, -1);
|
||||
@ -642,12 +912,18 @@ static void ata_enumerate(void)
|
||||
/** Detects (probably emulated) SCSI drives */
|
||||
static void sg_enumerate(void)
|
||||
{
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
|
||||
#else
|
||||
struct sg_scsi_id sid;
|
||||
int i, fd, sibling_fds[BURN_OS_SG_MAX_SIBLINGS], sibling_count= 0, ret;
|
||||
int sid_ret = 0;
|
||||
int bus_no= -1, host_no= -1, channel_no= -1, target_no= -1, lun_no= -1;
|
||||
char fname[10];
|
||||
int fd, sibling_fds[BURN_OS_SG_MAX_SIBLINGS], sibling_count= 0;
|
||||
char sibling_fnames[BURN_OS_SG_MAX_SIBLINGS][BURN_OS_SG_MAX_NAMELEN];
|
||||
int sid_ret = 0;
|
||||
#endif
|
||||
|
||||
int i, ret;
|
||||
int bus_no= -1, host_no= -1, channel_no= -1, target_no= -1, lun_no= -1;
|
||||
char fname[17];
|
||||
|
||||
sg_select_device_family();
|
||||
|
||||
@ -661,6 +937,9 @@ static void sg_enumerate(void)
|
||||
for (i = 0; i < 32; i++) {
|
||||
sprintf(fname, linux_sg_device_family, i);
|
||||
|
||||
/* ts A80702 */
|
||||
sg_exchange_scd_for_sr(fname, 0);
|
||||
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr, "libburn_debug: %s : ", fname);
|
||||
|
||||
@ -671,6 +950,23 @@ static void sg_enumerate(void)
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
|
||||
ret = is_scsi_drive(fname, &bus_no, &host_no, &channel_no,
|
||||
&target_no, &lun_no);
|
||||
if (ret < 0)
|
||||
break;
|
||||
if (ret == 0)
|
||||
continue;
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr, "accepting as SCSI %d,%d,%d,%d bus=%d\n",
|
||||
host_no, channel_no, target_no, lun_no, bus_no);
|
||||
enumerate_common(fname, bus_no, host_no, channel_no,
|
||||
target_no, lun_no);
|
||||
|
||||
#else /* Libburn_drive_new_deaL */
|
||||
|
||||
/* ts A60927 */
|
||||
fd = sg_open_drive_fd(fname, 1);
|
||||
if (fd == -1) {
|
||||
@ -780,16 +1076,223 @@ static void sg_enumerate(void)
|
||||
#else
|
||||
bus_no = sid.host_no;
|
||||
#endif
|
||||
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr, "accepting as SCSI %d,%d,%d,%d bus=%d\n",
|
||||
sid.host_no, sid.channel, sid.scsi_id, sid.lun,
|
||||
bus_no);
|
||||
enumerate_common(fname, bus_no, sid.host_no, sid.channel,
|
||||
sid.scsi_id, sid.lun);
|
||||
#endif /* Libburn_drive_new_deaL */
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
|
||||
|
||||
/* ts A80805 : eventually produce the other official name of a device file */
|
||||
static int fname_other_name(char *fname, char other_name[80], int flag)
|
||||
{
|
||||
if(strncmp(fname, "/dev/sr", 7) == 0 &&
|
||||
(fname[7] >= '0' && fname[7] <= '9') &&
|
||||
(fname[8] == 0 ||
|
||||
(fname[8] >= '0' && fname[8] <= '9' && fname[9] == 0))) {
|
||||
sprintf(other_name, "/dev/scd%s", fname + 7);
|
||||
return 1;
|
||||
}
|
||||
if(strncmp(fname, "/dev/scd", 8) == 0 &&
|
||||
(fname[8] >= '0' && fname[8] <= '9') &&
|
||||
(fname[9] == 0 ||
|
||||
(fname[9] >= '0' && fname[9] <= '9' && fname[10] == 0))) {
|
||||
sprintf(other_name, "/dev/sr%s", fname + 8);
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* ts A80805 */
|
||||
static int fname_drive_is_listed(char *fname, int flag)
|
||||
{
|
||||
char other_fname[80];
|
||||
|
||||
if (burn_drive_is_listed(fname, NULL, 0))
|
||||
return 1;
|
||||
if (fname_other_name(fname, other_fname, 0) > 0)
|
||||
if (burn_drive_is_listed(other_fname, NULL, 0))
|
||||
return 2;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* ts A80731 : Directly open the given address.
|
||||
@param flag bit0= do not complain about missing file
|
||||
bit1= do not check whether drive is already listed
|
||||
*/
|
||||
static int fname_enumerate(char *fname, int flag)
|
||||
{
|
||||
int is_ata= 0, is_scsi= 0;
|
||||
int bus_no= -1, host_no= -1, channel_no= -1, target_no= -1, lun_no= -1;
|
||||
char msg[BURN_DRIVE_ADR_LEN + 80];
|
||||
struct stat stbuf;
|
||||
|
||||
if (!(flag & 2))
|
||||
if (fname_drive_is_listed(fname, 0))
|
||||
return 2;
|
||||
if (stat(fname, &stbuf) == -1) {
|
||||
sprintf(msg, "File object '%s' not found", fname);
|
||||
if (!(flag & 1))
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x0002000b,
|
||||
LIBDAX_MSGS_SEV_FAILURE, LIBDAX_MSGS_PRIO_HIGH,
|
||||
msg, 0, 0);
|
||||
return -1;
|
||||
}
|
||||
|
||||
is_ata = is_ata_drive(fname);
|
||||
if (is_ata < 0)
|
||||
return -1;
|
||||
if (!is_ata)
|
||||
is_scsi = is_scsi_drive(fname, &bus_no, &host_no, &channel_no,
|
||||
&target_no, &lun_no);
|
||||
if (is_scsi < 0)
|
||||
return -1;
|
||||
if (is_ata == 0 && is_scsi == 0)
|
||||
return 0;
|
||||
|
||||
if (linux_sg_enumerate_debug)
|
||||
fprintf(stderr,
|
||||
"(single) accepting as SCSI %d,%d,%d,%d bus=%d\n",
|
||||
host_no, channel_no, target_no, lun_no, bus_no);
|
||||
enumerate_common(fname, bus_no, host_no, channel_no,
|
||||
target_no, lun_no);
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
/* ts A80731 : Directly open the given address from a single-item whitlist */
|
||||
static int single_enumerate(int flag)
|
||||
{
|
||||
int ret, wl_count;
|
||||
char *fname, msg[BURN_DRIVE_ADR_LEN + 80];
|
||||
|
||||
wl_count= burn_drive_whitelist_count();
|
||||
if (wl_count != 1)
|
||||
return 0;
|
||||
fname= burn_drive_whitelist_item(0, 0);
|
||||
if (fname == NULL)
|
||||
return 0;
|
||||
ret = fname_enumerate(fname, 2);
|
||||
if (ret <= 0) {
|
||||
sprintf(msg, "Cannot access '%s' as SG_IO CDROM drive", fname);
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x0002000a,
|
||||
LIBDAX_MSGS_SEV_FAILURE, LIBDAX_MSGS_PRIO_HIGH,
|
||||
msg, 0, 0);
|
||||
ret = -1;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/* ts A80801 : looking up drives listed in /proc/sys/dev/cdrom/info line like:
|
||||
drive name: sr1 hdc hda sr0
|
||||
@parm flag bit0= release list memory and exit
|
||||
*/
|
||||
static int proc_sys_dev_cdrom_info(char ***list, int *count, int flag)
|
||||
{
|
||||
FILE *fp;
|
||||
char line[1024], fname[1024 + 5], *cpt, *retpt, *list_data;
|
||||
int maxl= 0, pass, i;
|
||||
|
||||
if (*list != NULL) {
|
||||
if ((*list)[0] != NULL)
|
||||
free((*list)[0]);
|
||||
free(*list);
|
||||
*list = NULL;
|
||||
*count = 0;
|
||||
}
|
||||
if (flag & 1)
|
||||
return 1;
|
||||
|
||||
*count = 0;
|
||||
sg_evaluate_kernel();
|
||||
if (sg_kernel_age < 2) /* addresses are not suitable for kernel 2.4 */
|
||||
return 1;
|
||||
fp = fopen("/proc/sys/dev/cdrom/info", "r");
|
||||
if (fp == NULL)
|
||||
return 0;
|
||||
while (1) {
|
||||
retpt = fgets(line, sizeof(line), fp);
|
||||
if (retpt == NULL)
|
||||
break;
|
||||
if(strncmp(line, "drive name:", 11) == 0)
|
||||
break;
|
||||
}
|
||||
fclose(fp);
|
||||
if (retpt == NULL)
|
||||
return 0;
|
||||
strcpy(fname, "/dev/");
|
||||
for(pass = 0; pass < 2; pass++) {
|
||||
*count = 0;
|
||||
cpt = line + 11;
|
||||
while (*cpt != 0) {
|
||||
for(; *cpt == ' ' || *cpt == '\t'; cpt++);
|
||||
if (*cpt == 0 || *cpt == '\n')
|
||||
break;
|
||||
sscanf(cpt, "%s", fname + 5);
|
||||
if (strlen(fname) > maxl)
|
||||
maxl = strlen(fname);
|
||||
if (pass == 1)
|
||||
strcpy((*list)[*count], fname);
|
||||
(*count)++;
|
||||
for(cpt++; *cpt != ' ' && *cpt != '\t'
|
||||
&& *cpt != 0 && *cpt != '\n'; cpt++);
|
||||
}
|
||||
if (pass == 0) {
|
||||
list_data = calloc(*count + 1, maxl+1);
|
||||
*list = calloc(*count + 1, sizeof(char *));
|
||||
if(list_data == NULL || *list == NULL) {
|
||||
libdax_msgs_submit(libdax_messenger, -1,
|
||||
0x00000003,
|
||||
LIBDAX_MSGS_SEV_FATAL, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"Out of virtual memory", 0, 0);
|
||||
if (list_data != NULL)
|
||||
free(list_data);
|
||||
if (*list != NULL)
|
||||
free((char *) *list);
|
||||
return -1;
|
||||
}
|
||||
for (i = 0; i <= *count; i++)
|
||||
(*list)[i] = list_data + i * (maxl + 1);
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
static int add_proc_info_drives(int flag)
|
||||
{
|
||||
int ret, list_count, count = 0, i;
|
||||
char **list= NULL;
|
||||
|
||||
ret = proc_sys_dev_cdrom_info(&list, &list_count, 0);
|
||||
if (ret <= 0)
|
||||
return ret;
|
||||
for (i = 0; i < list_count; i++) {
|
||||
if (burn_drive_is_banned(list[i]))
|
||||
continue;
|
||||
ret = fname_enumerate(list[i], 1);
|
||||
if (ret == 1)
|
||||
count++;
|
||||
}
|
||||
proc_sys_dev_cdrom_info(&list, &list_count, 1); /* free memory */
|
||||
return 1 + count;
|
||||
}
|
||||
|
||||
#endif /* Libburn_drive_new_deaL */
|
||||
|
||||
|
||||
/* ts A61115 */
|
||||
/* ----------------------------------------------------------------------- */
|
||||
/* PORTING: Private functions which contain publicly needed functionality. */
|
||||
@ -874,10 +1377,14 @@ int sg_give_next_adr(burn_drive_enumerator_t *idx,
|
||||
{
|
||||
/* os-linux.h : typedef int burn_drive_enumerator_t; */
|
||||
static int sg_limit = 32, ata_limit = 26;
|
||||
int baseno = 0;
|
||||
int baseno = 0, i;
|
||||
char other_name[80];
|
||||
|
||||
if (initialize == -1)
|
||||
if (initialize == -1) {
|
||||
proc_sys_dev_cdrom_info(&(idx->info_list), &(idx->info_count),
|
||||
1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
sg_select_device_family();
|
||||
if (linux_sg_device_family[0] == 0)
|
||||
@ -885,26 +1392,56 @@ int sg_give_next_adr(burn_drive_enumerator_t *idx,
|
||||
if (linux_ata_device_family[0] == 0)
|
||||
ata_limit = 0;
|
||||
|
||||
if (initialize == 1)
|
||||
*idx = -1;
|
||||
(*idx)++;
|
||||
if (*idx >= sg_limit)
|
||||
if (initialize == 1) {
|
||||
idx->pos = -1;
|
||||
idx->info_count= 0;
|
||||
idx->info_list= NULL;
|
||||
proc_sys_dev_cdrom_info(&(idx->info_list), &(idx->info_count),
|
||||
0);
|
||||
}
|
||||
(idx->pos)++;
|
||||
if (idx->pos >= sg_limit)
|
||||
goto next_ata;
|
||||
if (adr_size < 10)
|
||||
if (adr_size < 11)
|
||||
return -1;
|
||||
sprintf(adr, linux_sg_device_family, *idx);
|
||||
return 1;
|
||||
sprintf(adr, linux_sg_device_family, idx->pos);
|
||||
|
||||
sg_exchange_scd_for_sr(adr, 0);
|
||||
goto return_1_pre_proc;
|
||||
|
||||
next_ata:;
|
||||
baseno += sg_limit;
|
||||
if (*idx - baseno >= ata_limit)
|
||||
goto next_nothing;
|
||||
if (idx->pos - baseno >= ata_limit)
|
||||
goto next_proc_info;
|
||||
if (adr_size < 9)
|
||||
return -1;
|
||||
sprintf(adr, linux_ata_device_family, 'a' + (*idx - baseno));
|
||||
return 1;
|
||||
next_nothing:;
|
||||
sprintf(adr, linux_ata_device_family, 'a' + (idx->pos - baseno));
|
||||
goto return_1_pre_proc;
|
||||
|
||||
next_proc_info:;
|
||||
baseno += ata_limit;
|
||||
for (i = 0; i < idx->info_count; i++) {
|
||||
if ((idx->info_list)[i][0] == 0)
|
||||
continue;
|
||||
if (baseno == idx->pos) {
|
||||
if (adr_size < strlen((idx->info_list)[i]) + 1)
|
||||
return -1;
|
||||
strcpy(adr, (idx->info_list)[i]);
|
||||
return 1;
|
||||
}
|
||||
baseno++;
|
||||
}
|
||||
return 0;
|
||||
|
||||
return_1_pre_proc:;
|
||||
for (i = 0; i < idx->info_count; i++) {
|
||||
if (strcmp((idx->info_list)[i], adr) == 0)
|
||||
(idx->info_list)[i][0] = 0;
|
||||
if (fname_other_name(adr, other_name, 0) > 0)
|
||||
if (strcmp((idx->info_list)[i], other_name) == 0)
|
||||
(idx->info_list)[i][0] = 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
@ -926,8 +1463,27 @@ next_nothing:;
|
||||
/* ts A61115: replacing call to sg-implementation internals from drive.c */
|
||||
int scsi_enumerate_drives(void)
|
||||
{
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
int ret;
|
||||
#endif
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
/* Direct examination of eventually single whitelisted name */
|
||||
ret = single_enumerate(0);
|
||||
if (ret < 0)
|
||||
return -1;
|
||||
if (ret > 0)
|
||||
return 1;
|
||||
#endif /* Libburn_drive_new_deaL */
|
||||
|
||||
sg_enumerate();
|
||||
ata_enumerate();
|
||||
|
||||
#ifdef Libburn_drive_new_deaL
|
||||
add_proc_info_drives(0);
|
||||
#endif /* Libburn_drive_new_deaL */
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -1378,9 +1934,9 @@ int sg_is_enumerable_adr(char *adr)
|
||||
sg_give_next_adr(&idx, fname, sizeof(fname), -1);
|
||||
return 1;
|
||||
}
|
||||
|
||||
}
|
||||
sg_give_next_adr(&idx, fname, sizeof(fname), -1);
|
||||
if (first == 0)
|
||||
sg_give_next_adr(&idx, fname, sizeof(fname), -1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
255
libburn/spc.c
255
libburn/spc.c
@ -117,9 +117,9 @@ int spc_wait_unit_attention(struct burn_drive *d, int max_sec, char *cmd_text,
|
||||
i, ret, (unsigned) key, (unsigned) asc, (unsigned) ascq);
|
||||
*/
|
||||
|
||||
if(ret > 0) /* ready */
|
||||
if (ret > 0) /* ready */
|
||||
break;
|
||||
if(key!=0x2 || asc!=0x4) {
|
||||
if (key!=0x2 || asc!=0x4) {
|
||||
if (key == 0x2 && asc == 0x3A) {
|
||||
ret = 1; /* medium not present = ok */
|
||||
/* <<<
|
||||
@ -568,7 +568,7 @@ void spc_sense_write_params(struct burn_drive *d)
|
||||
|
||||
/* ts A71128 : do not interpret reply if error */
|
||||
m = d->mdata;
|
||||
if(!c.error) {
|
||||
if (!c.error) {
|
||||
size = c.page->data[0] * 256 + c.page->data[1];
|
||||
page = c.page->data + 8;
|
||||
burn_print(1, "write page length 0x%x\n", page[1]);
|
||||
@ -845,7 +845,7 @@ int burn_scsi_setup_drive(struct burn_drive *d, int bus_no, int host_no,
|
||||
d->mdata = calloc(1, sizeof(struct scsi_mode_data));
|
||||
|
||||
/* ts A61007 : obsolete Assert in drive_getcaps() */
|
||||
if(d->idata == NULL || d->mdata == NULL) {
|
||||
if (d->idata == NULL || d->mdata == NULL) {
|
||||
libdax_msgs_submit(libdax_messenger, -1, 0x00020108,
|
||||
LIBDAX_MSGS_SEV_FATAL, LIBDAX_MSGS_PRIO_HIGH,
|
||||
"Could not allocate new drive object", 0, 0);
|
||||
@ -854,7 +854,7 @@ int burn_scsi_setup_drive(struct burn_drive *d, int bus_no, int host_no,
|
||||
d->idata->valid = 0;
|
||||
d->mdata->valid = 0;
|
||||
d->mdata->speed_descriptors = NULL;
|
||||
if(!(flag & 1)) {
|
||||
if (!(flag & 1)) {
|
||||
ret = spc_setup_drive(d);
|
||||
if (ret<=0)
|
||||
return ret;
|
||||
@ -869,11 +869,14 @@ int burn_scsi_setup_drive(struct burn_drive *d, int bus_no, int host_no,
|
||||
}
|
||||
|
||||
|
||||
/* ts A61122 */
|
||||
/* ts A61122 - A80829 */
|
||||
enum response scsi_error_msg(struct burn_drive *d, unsigned char *sense,
|
||||
int senselen, char msg[161],
|
||||
int senselen, char msg_data[161],
|
||||
int *key, int *asc, int *ascq)
|
||||
{
|
||||
char *msg;
|
||||
|
||||
msg= msg_data;
|
||||
*key= *asc= *ascq= -1;
|
||||
|
||||
if (senselen<=0 || senselen>2)
|
||||
@ -883,50 +886,236 @@ enum response scsi_error_msg(struct burn_drive *d, unsigned char *sense,
|
||||
if (senselen<=0 || senselen>13)
|
||||
*ascq = sense[13];
|
||||
|
||||
sprintf(msg, "[%X %2.2X %2.2X] ", *key, *asc, *ascq);
|
||||
msg= msg + strlen(msg);
|
||||
|
||||
burn_print(12, "CONDITION: 0x%x 0x%x 0x%x on %s %s\n",
|
||||
*key, *asc, *ascq, d->idata->vendor, d->idata->product);
|
||||
|
||||
switch (*asc) {
|
||||
case 0:
|
||||
sprintf(msg, "(no error reported by SCSI transaction)");
|
||||
case 0x00:
|
||||
sprintf(msg, "(No error reported by SCSI transaction)");
|
||||
return RETRY;
|
||||
|
||||
case 2:
|
||||
sprintf(msg, "not ready");
|
||||
case 0x02:
|
||||
sprintf(msg, "Not ready");
|
||||
return RETRY;
|
||||
case 4:
|
||||
case 0x04:
|
||||
sprintf(msg,
|
||||
"logical unit is in the process of becoming ready");
|
||||
"Logical unit is in the process of becoming ready");
|
||||
return RETRY;
|
||||
case 0x09:
|
||||
if (*key != 4)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg, "Track following error");
|
||||
else if (*ascq == 1)
|
||||
sprintf(msg, "Tracking servo failure");
|
||||
else if (*ascq == 2)
|
||||
sprintf(msg, "Focus servo failure");
|
||||
else if (*ascq == 3)
|
||||
sprintf(msg, "Spindle servo failure");
|
||||
else if (*ascq == 4)
|
||||
sprintf(msg, "Head select fault");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
case 0x0C:
|
||||
if (*key == 2 && *ascq == 7)
|
||||
sprintf(msg, "Write error, recovery needed");
|
||||
else if (*key == 2 && *ascq == 0x0f)
|
||||
sprintf(msg, "Defects in error window");
|
||||
else if (*key == 3 && *ascq == 2)
|
||||
sprintf(msg, "Write error, auto reallocation failed");
|
||||
else if (*key == 3 && *ascq == 9)
|
||||
sprintf(msg, "Write error, loss of streaming");
|
||||
else if (*key == 3)
|
||||
sprintf(msg, "Write error");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
case 0x11:
|
||||
if (*key != 3)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg, "Unrecovered read error");
|
||||
else if (*ascq == 1)
|
||||
sprintf(msg, "Read retries exhausted");
|
||||
else if (*ascq == 2)
|
||||
sprintf(msg, "Error too long to correct");
|
||||
else if (*ascq == 5)
|
||||
sprintf(msg, "L-EC uncorrectable error");
|
||||
else if (*ascq == 6)
|
||||
sprintf(msg, "CIRC uncorrectable error");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
case 0x15:
|
||||
if (*key != 3 && *key != 4)
|
||||
break;
|
||||
sprintf(msg, "Random positioning error");
|
||||
return FAIL;
|
||||
case 0x1a:
|
||||
if (*key != 5)
|
||||
break;
|
||||
sprintf(msg, "Parameter list length error");
|
||||
return FAIL;
|
||||
case 0x1b:
|
||||
if (*key != 4)
|
||||
break;
|
||||
sprintf(msg, "Synchronous data transfer error");
|
||||
return FAIL;
|
||||
case 0x20:
|
||||
if (*key == 5)
|
||||
sprintf(msg, "bad opcode");
|
||||
if (*key != 5)
|
||||
break;
|
||||
sprintf(msg, "Invalid command operation code");
|
||||
return FAIL;
|
||||
case 0x21:
|
||||
sprintf(msg, "invalid address");
|
||||
if (*key != 5)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg, "Lba out of range");
|
||||
else if (*ascq == 3)
|
||||
sprintf(msg, "Invalid write crossing layer jump");
|
||||
else
|
||||
sprintf(msg, "Invalid address");
|
||||
return FAIL;
|
||||
case 0x24:
|
||||
if (*key == 5)
|
||||
sprintf(msg, "invalid field in cdb");
|
||||
else
|
||||
if (*key != 5)
|
||||
break;
|
||||
sprintf(msg, "Invalid field in cdb");
|
||||
return FAIL;
|
||||
case 0x26:
|
||||
if (*key == 5 )
|
||||
sprintf(msg, "invalid field in parameter list" );
|
||||
if (*key != 5)
|
||||
break;
|
||||
if (*ascq == 1)
|
||||
sprintf(msg, "Parameter not supported");
|
||||
else if (*ascq == 2)
|
||||
sprintf(msg, "Parameter value invalid");
|
||||
else
|
||||
sprintf(msg, "Invalid field in parameter list");
|
||||
return FAIL;
|
||||
case 0x27:
|
||||
if (*key != 7)
|
||||
break;
|
||||
sprintf(msg, "Write protected");
|
||||
return FAIL;
|
||||
case 0x28:
|
||||
if (*key == 6)
|
||||
if (*key != 6)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg, "Medium may have changed");
|
||||
else if (*ascq == 2)
|
||||
sprintf(msg, "Format layer may have changed");
|
||||
else
|
||||
break;
|
||||
return RETRY;
|
||||
case 0x29:
|
||||
if (*key != 6)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg,
|
||||
"Power on, reset, or bus device reset occured");
|
||||
else if (*ascq == 1)
|
||||
sprintf(msg, "Power on occured");
|
||||
else if (*ascq == 2)
|
||||
sprintf(msg, "Bus reset occured");
|
||||
else if (*ascq == 3)
|
||||
sprintf(msg, "Bus device reset function occured");
|
||||
else if (*ascq == 4)
|
||||
sprintf(msg, "Device internal reset");
|
||||
else
|
||||
break;
|
||||
return RETRY;
|
||||
case 0x2c:
|
||||
if (*key != 5)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg, "Command sequence error");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
case 0x2e:
|
||||
if (*key != 6)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg,
|
||||
"Insufficient time for operation");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
case 0x30:
|
||||
if (*key != 2 && *key != 5)
|
||||
break;
|
||||
if (*ascq == 1)
|
||||
sprintf(msg, "Cannot read medium, unknown format");
|
||||
else if (*ascq == 2)
|
||||
sprintf(msg,
|
||||
"Cannot read medium, incompatible format");
|
||||
else if (*ascq == 4)
|
||||
sprintf(msg, "Cannot write medium, unknown format");
|
||||
else if (*ascq == 5)
|
||||
sprintf(msg,
|
||||
"Cannot write medium, incompatible format");
|
||||
else if (*ascq == 6)
|
||||
sprintf(msg,
|
||||
"Cannot format medium, incompatible medium");
|
||||
else if (*ascq == 7)
|
||||
sprintf(msg, "Cleaning failure");
|
||||
else
|
||||
sprintf(msg, "Incompatible medium installed");
|
||||
return FAIL;
|
||||
case 0x3A:
|
||||
sprintf(msg, "Medium not present");
|
||||
if (*key != 2)
|
||||
break;
|
||||
if (*ascq == 1)
|
||||
sprintf(msg, "Medium not present, tray closed");
|
||||
else if (*ascq == 2)
|
||||
sprintf(msg, "Medium not present, tray open");
|
||||
else if (*ascq == 3)
|
||||
sprintf(msg, "Medium not present, loadable");
|
||||
else
|
||||
sprintf(msg, "Medium not present");
|
||||
d->status = BURN_DISC_EMPTY;
|
||||
return FAIL;
|
||||
case 0x63:
|
||||
if (*key != 5)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg,
|
||||
"End of user area encountered on this track");
|
||||
else if (*ascq == 1)
|
||||
sprintf(msg, "Packet does not fit in available space");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
case 0x64:
|
||||
if (*key != 5)
|
||||
break;
|
||||
if (*ascq == 0)
|
||||
sprintf(msg, "Illegal mode for this track");
|
||||
else if (*ascq == 1)
|
||||
sprintf(msg, "Invalid packet size");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
case 0x72:
|
||||
if (*key == 3)
|
||||
sprintf(msg, "Session fixation error");
|
||||
else if (*key == 5 && *ascq == 3)
|
||||
sprintf(msg,
|
||||
"Session fixation error, incomplete track in session");
|
||||
else if (*key == 5 && *ascq == 4)
|
||||
sprintf(msg,
|
||||
"Empty or partially written reserved track");
|
||||
else if (*key == 5 && *ascq == 5)
|
||||
sprintf(msg,
|
||||
"No more track reservations allowed");
|
||||
else
|
||||
break;
|
||||
return FAIL;
|
||||
}
|
||||
sprintf(msg,
|
||||
sprintf(msg_data,
|
||||
"Failure. See mmc3r10g.pdf: Sense Key %X ASC %2.2X ASCQ %2.2X",
|
||||
*key, *asc, *ascq);
|
||||
return FAIL;
|
||||
@ -962,12 +1151,9 @@ int scsi_notify_error(struct burn_drive *d, struct command *c,
|
||||
if (d->silent_on_scsi_error)
|
||||
return 1;
|
||||
|
||||
strcpy(scsi_msg, " \"");
|
||||
scsi_error_msg(d, sense, senselen, scsi_msg + strlen(scsi_msg),
|
||||
&key, &asc, &ascq);
|
||||
strcat(scsi_msg, "\"");
|
||||
scsi_error_msg(d, sense, senselen, scsi_msg, &key, &asc, &ascq);
|
||||
|
||||
if(!(flag & 1)) {
|
||||
if (!(flag & 1)) {
|
||||
/* SPC : TEST UNIT READY command */
|
||||
if (c->opcode[0] == 0)
|
||||
return 1;
|
||||
@ -978,7 +1164,9 @@ int scsi_notify_error(struct burn_drive *d, struct command *c,
|
||||
return 1;
|
||||
}
|
||||
|
||||
sprintf(msg,"SCSI error condition on command %2.2Xh :", c->opcode[0]);
|
||||
sprintf(msg,"SCSI error condition on command %2.2Xh : ", c->opcode[0]);
|
||||
|
||||
#ifdef NIX
|
||||
if (key>=0)
|
||||
sprintf(msg+strlen(msg), " key=%Xh", key);
|
||||
if (asc>=0)
|
||||
@ -992,6 +1180,13 @@ int scsi_notify_error(struct burn_drive *d, struct command *c,
|
||||
ret = libdax_msgs_submit(libdax_messenger, d->global_index, 0x0002010f,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_HIGH,
|
||||
scsi_msg,0,0);
|
||||
#else
|
||||
strcat(msg, scsi_msg);
|
||||
ret = libdax_msgs_submit(libdax_messenger, d->global_index, 0x0002010f,
|
||||
LIBDAX_MSGS_SEV_DEBUG, LIBDAX_MSGS_PRIO_HIGH, msg,0,0);
|
||||
|
||||
#endif /* NIX */
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -330,11 +330,19 @@ void burn_track_clear_isrc(struct burn_track *t)
|
||||
int burn_track_get_sectors(struct burn_track *t)
|
||||
{
|
||||
/* ts A70125 : was int */
|
||||
off_t size;
|
||||
off_t size = 0;
|
||||
int sectors, seclen;
|
||||
|
||||
seclen = burn_sector_length(t->mode);
|
||||
size = t->offset + t->source->get_size(t->source) + t->tail;
|
||||
if (t->source != NULL) /* ts A80808 : mending sigsegv */
|
||||
size = t->offset + t->source->get_size(t->source) + t->tail;
|
||||
else if(t->entry != NULL) {
|
||||
/* ts A80808 : all burn_toc_entry of track starts should now
|
||||
have (extensions_valid & 1), even those from CD.
|
||||
*/
|
||||
if (t->entry->extensions_valid & 1)
|
||||
size = ((off_t) t->entry->track_blocks) * (off_t) 2048;
|
||||
}
|
||||
sectors = size / seclen;
|
||||
if (size % seclen)
|
||||
sectors++;
|
||||
@ -468,6 +476,7 @@ int burn_session_get_sectors(struct burn_session *s)
|
||||
return sectors;
|
||||
}
|
||||
|
||||
|
||||
int burn_disc_get_sectors(struct burn_disc *d)
|
||||
{
|
||||
int sectors = 0, i;
|
||||
@ -515,3 +524,40 @@ int burn_session_get_hidefirst(struct burn_session *session)
|
||||
{
|
||||
return session->hidefirst;
|
||||
}
|
||||
|
||||
|
||||
/* ts A80808 : Enhance CD toc to DVD toc */
|
||||
int burn_disc_cd_toc_extensions(struct burn_disc *d, int flag)
|
||||
{
|
||||
int sidx, tidx;
|
||||
struct burn_toc_entry *entry, *prev_entry= NULL;
|
||||
|
||||
for (sidx = 0; sidx < d->sessions; sidx++) {
|
||||
for (tidx = 0; tidx < d->session[sidx]->tracks + 1; tidx++) {
|
||||
if (tidx < d->session[sidx]->tracks)
|
||||
entry = d->session[sidx]->track[tidx]->entry;
|
||||
else
|
||||
entry = d->session[sidx]->leadout_entry;
|
||||
entry->session_msb = 0;
|
||||
entry->point_msb = 0;
|
||||
entry->start_lba = burn_msf_to_lba(entry->pmin,
|
||||
entry->psec, entry->pframe);
|
||||
if (tidx > 0) {
|
||||
prev_entry->track_blocks =
|
||||
entry->start_lba
|
||||
- prev_entry->start_lba;
|
||||
prev_entry->extensions_valid |= 1;
|
||||
}
|
||||
if (tidx == d->session[sidx]->tracks) {
|
||||
entry->session_msb = 0;
|
||||
entry->point_msb = 0;
|
||||
entry->track_blocks = 0;
|
||||
entry->extensions_valid |= 1;
|
||||
}
|
||||
prev_entry = entry;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
|
@ -109,4 +109,8 @@ int burn_track_apply_fillup(struct burn_track *t, off_t max_size, int flag);
|
||||
off_t burn_track_get_default_size(struct burn_track *t);
|
||||
|
||||
|
||||
/* ts A80808 : Enhance CD toc to DVD toc */
|
||||
int burn_disc_cd_toc_extensions(struct burn_disc *d, int flag);
|
||||
|
||||
|
||||
#endif /* BURN__STRUCTURE_H */
|
||||
|
@ -4,7 +4,11 @@
|
||||
/* #include <a ssert.h> */
|
||||
|
||||
#include <stdlib.h>
|
||||
#include "../version.h"
|
||||
|
||||
/* ts A80914 : This is unneeded. Version info comes from libburn.h.
|
||||
#include "v ersion.h"
|
||||
*/
|
||||
|
||||
#include "util.h"
|
||||
#include "libburn.h"
|
||||
|
||||
@ -48,13 +52,7 @@ char *burn_strndup(char *s, int n)
|
||||
void burn_version(int *major, int *minor, int *micro)
|
||||
{
|
||||
/* ts A80408 : switched from configure.ac versioning to libburn.h versioning */
|
||||
#ifdef burn_header_version_major
|
||||
*major = burn_header_version_major;
|
||||
*minor = burn_header_version_minor;
|
||||
*micro = burn_header_version_micro;
|
||||
#else
|
||||
*major = BURN_MAJOR_VERSION;
|
||||
*minor = BURN_MINOR_VERSION;
|
||||
*micro = BURN_MICRO_VERSION;
|
||||
#endif
|
||||
*major = burn_header_version_major;
|
||||
*minor = burn_header_version_minor;
|
||||
*micro = burn_header_version_micro;
|
||||
}
|
||||
|
@ -1996,7 +1996,7 @@ void burn_disc_write_sync(struct burn_write_opts *o, struct burn_disc *disc)
|
||||
{
|
||||
struct cue_sheet *sheet;
|
||||
struct burn_drive *d = o->drive;
|
||||
struct buffer buf;
|
||||
struct buffer buf, *buffer_mem = o->drive->buffer;
|
||||
struct burn_track *lt, *t;
|
||||
int first = 1, i, ret, lba, nwa = 0;
|
||||
off_t default_size;
|
||||
@ -2206,6 +2206,7 @@ fail_wo_sync:;
|
||||
d->busy = BURN_DRIVE_IDLE;
|
||||
ex:;
|
||||
d->do_stream_recording = 0;
|
||||
d->buffer = buffer_mem;
|
||||
return;
|
||||
}
|
||||
|
||||
@ -2215,7 +2216,7 @@ int burn_random_access_write(struct burn_drive *d, off_t byte_address,
|
||||
{
|
||||
int alignment = 0, start, upto, chunksize, err, fd = -1, ret;
|
||||
char msg[81], *rpt;
|
||||
struct buffer buf;
|
||||
struct buffer buf, *buffer_mem = d->buffer;
|
||||
|
||||
if (d->released) {
|
||||
libdax_msgs_submit(libdax_messenger,
|
||||
@ -2326,7 +2327,7 @@ int burn_random_access_write(struct burn_drive *d, off_t byte_address,
|
||||
|
||||
if(fd >= 0)
|
||||
close(fd);
|
||||
d->buffer = NULL;
|
||||
d->buffer = buffer_mem;
|
||||
d->busy = BURN_DRIVE_IDLE;
|
||||
return 1;
|
||||
}
|
||||
|
Reference in New Issue
Block a user