git: b9811d13572b - main - cd9660: merge level 1 and 2 filename conversion
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Thu, 24 Sep 2026 15:10:39 UTC
The branch main has been updated by emaste:
URL: https://cgit.FreeBSD.org/src/commit/?id=b9811d13572b93adff2da16508eef18872b24c85
commit b9811d13572b93adff2da16508eef18872b24c85
Author: Manuel Einfalt <einfalt1@proton.me>
AuthorDate: 2026-09-23 15:04:25 +0000
Commit: Ed Maste <emaste@FreeBSD.org>
CommitDate: 2026-09-24 15:07:51 +0000
cd9660: merge level 1 and 2 filename conversion
Merge the nearly identical level 1 and level 2 filename conversion
functions and add output buffer bounds checking.
Always NUL-terminate the converted filename, allowing the redundant
memset() in cd9660_translate_node_common() to be removed.
Signed-off-by: Manuel Einfalt <einfalt1@proton.me>
Reviewed by: emaste
Pull request: https://github.com/freebsd/freebsd-src/pull/2443
---
usr.sbin/makefs/cd9660.c | 129 +++++++++++++----------------------------------
1 file changed, 35 insertions(+), 94 deletions(-)
diff --git a/usr.sbin/makefs/cd9660.c b/usr.sbin/makefs/cd9660.c
index 687bfe46ac27..cf004f22ecdd 100644
--- a/usr.sbin/makefs/cd9660.c
+++ b/usr.sbin/makefs/cd9660.c
@@ -139,10 +139,6 @@ static void cd9660_convert_structure(iso9660_disk *, fsnode *, cd9660node *, int
int *, int *);
static void cd9660_free_structure(cd9660node *);
static int cd9660_generate_path_table(iso9660_disk *);
-static int cd9660_level1_convert_filename(iso9660_disk *, const char *, char *,
- size_t, int);
-static int cd9660_level2_convert_filename(iso9660_disk *, const char *, char *,
- size_t, int);
static int cd9660_convert_filename(iso9660_disk *, const char *, char *, size_t,
int);
static void cd9660_populate_dot_records(iso9660_disk *, cd9660node *);
@@ -799,8 +795,6 @@ cd9660_translate_node_common(iso9660_disk *diskStructure, cd9660node *newnode)
char temp[ISO_FILENAME_MAXLENGTH];
/* Now populate the isoDirRecord structure */
- memset(temp, 0, sizeof(temp));
-
(void)cd9660_convert_filename(diskStructure, newnode->node->name,
temp, sizeof(temp), !(S_ISDIR(newnode->node->type)));
@@ -1564,13 +1558,15 @@ cd9660_compute_full_filename(cd9660node *node, char *buf)
}
/*
- * TODO: These two functions are almost identical.
- * Some code cleanup is possible here
- *
- * XXX bounds checking!
+ * Convert a file name to ISO compliant file name
+ * @param char * oldname The original filename
+ * @param char ** newname The new file name, in the appropriate character
+ * set and of appropriate length
+ * @param int 1 if file, 0 if directory
+ * @returns int The length of the new string
*/
static int
-cd9660_level1_convert_filename(iso9660_disk *diskStructure, const char *oldname,
+cd9660_convert_filename(iso9660_disk *diskStructure, const char *oldname,
char *newname, size_t newnamelen, int is_file)
{
/*
@@ -1578,58 +1574,7 @@ cd9660_level1_convert_filename(iso9660_disk *diskStructure, const char *oldname,
* File Name shall not contain more than 8 d or d1 characters
* File Name Extension shall not contain more than 3 d or d1 characters
* Directory Identifier shall not contain more than 8 d or d1 characters
- */
- int namelen = 0;
- int extlen = 0;
- int found_ext = 0;
- char *orignewname = newname;
-
- while (*oldname != '\0' && extlen < 3) {
- /* Handle period first, as it is special */
- if (*oldname == '.') {
- if (found_ext) {
- *newname++ = '_';
- extlen ++;
- }
- else {
- *newname++ = '.';
- found_ext = 1;
- }
- } else {
- /* Enforce 12.3 / 8 */
- if (namelen == 8 && !found_ext)
- break;
-
- if (islower((unsigned char)*oldname))
- *newname++ = toupper((unsigned char)*oldname);
- else if (isupper((unsigned char)*oldname)
- || isdigit((unsigned char)*oldname))
- *newname++ = *oldname;
- else
- *newname++ = '_';
-
- if (found_ext)
- extlen++;
- else
- namelen++;
- }
- oldname++;
- }
- if (is_file) {
- if (!found_ext && !diskStructure->omit_trailing_period)
- *newname++ = '.';
- /* Add version */
- snprintf(newname, newnamelen - (newname - orignewname), ";%i", 1);
- }
- return namelen + extlen + found_ext;
-}
-
-/* XXX bounds checking! */
-static int
-cd9660_level2_convert_filename(iso9660_disk *diskStructure, const char *oldname,
- char *newname, size_t newnamelen, int is_file)
-{
- /*
+ *
* ISO 9660 : 7.5.1
* File name : 0+ d or d1 characters
* separator 1 (.)
@@ -1638,28 +1583,44 @@ cd9660_level2_convert_filename(iso9660_disk *diskStructure, const char *oldname,
* File version number (5 characters, 1-32767)
* 1 <= Sum of File name and File name extension <= 30
*/
- int maxlen = is_file ? 30 : 31;
int namelen = 0;
int extlen = 0;
int found_ext = 0;
char *orignewname = newname;
+ int level;
+ int maxlen = is_file ? 30 : 31;
+ size_t suffix_len = is_file ? 3 : 1;
+
+ assert(diskStructure->isoLevel == 1 || diskStructure->isoLevel == 2);
+ assert(newnamelen >= 4); /* at least enough memory for "[char];1\0" */
- while (*oldname != '\0' && namelen + extlen < maxlen) {
+ level = diskStructure->isoLevel;
+ while ((newnamelen - (newname - orignewname) > suffix_len)
+ && (*oldname != '\0' && ((level == 1 && extlen < 3)
+ || (level == 2 && namelen + extlen < maxlen)))) {
/* Handle period first, as it is special */
- if (*oldname == '.' && is_file) {
+ if (*oldname == '.' && (level == 1 || (level == 2 && is_file))) {
if (found_ext) {
- if (diskStructure->allow_multidot) {
- *newname++ = '.';
- } else {
+ if (level == 1)
*newname++ = '_';
+ else if (level == 2) {
+ if (diskStructure->allow_multidot) {
+ *newname++ = '.';
+ } else {
+ *newname++ = '_';
+ }
}
- extlen ++;
+ extlen++;
}
else {
*newname++ = '.';
found_ext = 1;
}
} else {
+ /* Enforce 12.3 / 8 */
+ if (level == 1 && namelen == 8 && !found_ext)
+ break;
+
if (islower((unsigned char)*oldname))
*newname++ = toupper((unsigned char)*oldname);
else if (isupper((unsigned char)*oldname) ||
@@ -1673,37 +1634,17 @@ cd9660_level2_convert_filename(iso9660_disk *diskStructure, const char *oldname,
else
namelen++;
}
- oldname ++;
+ oldname++;
}
if (is_file) {
if (!found_ext && !diskStructure->omit_trailing_period)
*newname++ = '.';
/* Add version */
snprintf(newname, newnamelen - (newname - orignewname), ";%i", 1);
- }
- return namelen + extlen + found_ext;
-}
+ } else
+ *newname = '\0';
-/*
- * Convert a file name to ISO compliant file name
- * @param char * oldname The original filename
- * @param char ** newname The new file name, in the appropriate character
- * set and of appropriate length
- * @param int 1 if file, 0 if directory
- * @returns int The length of the new string
- */
-static int
-cd9660_convert_filename(iso9660_disk *diskStructure, const char *oldname,
- char *newname, size_t newnamelen, int is_file)
-{
- assert(1 <= diskStructure->isoLevel && diskStructure->isoLevel <= 2);
- if (diskStructure->isoLevel == 1)
- return(cd9660_level1_convert_filename(diskStructure,
- oldname, newname, newnamelen, is_file));
- else if (diskStructure->isoLevel == 2)
- return (cd9660_level2_convert_filename(diskStructure,
- oldname, newname, newnamelen, is_file));
- abort();
+ return (namelen + extlen + found_ext);
}
int