Re: [hatari-devel] Re: Feature request: allow to specify "-d" with autostart

[ Thread Index | Date Index | More lists.tuxfamily.org/hatari-devel Archives ]


Hi,

Some comments:

* "-d" option is already used for specifying GEMDOS HD directory
  (if you specify e.g. floppy image after that on command line,
   then A: is the boot drive, not GEMDOS HD C:)

* For autoexec to work, boot drive must be GEMDOS HD
  (because it works by hooking TOS *.INF file read, and
   TOS reads that only from boot drive)

* Currently Hatari validates that autoexecuted program path and
  file are OK.  This cannot be done if the option doesn't know
  where it will be in the file system hierarchy, which would be
  the case with your proposal


Instead, my proposal is an option for specifying the autostarted
program with full path:
  --auto <x>            Atari program autostarting with Atari path

Attached is a patch implementing that.  Only validation it does
is that the drive letter isn't obviously bogus.


	- Eero

On 03/28/2017 05:43 AM, Miro Kropáček wrote:
... but not working for "Atari program", it works only for specifying
directory. So after all, I do have one feature request/bug report, please
please make it work with "Atari program" command line parameter as well.

On 28 March 2017 at 12:36, Miro Kropáček <miro.kropacek@xxxxxxxxx> wrote:

OK, after RTFM I've realised the feature is actually there. Thanks
--gemdos-drive and --acsi!

On 28 March 2017 at 12:16, Miro Kropáček <miro.kropacek@xxxxxxxxx> wrote:

And while are we at it, why limit it to "-d" (i.e. gemdos drive), having
this with any (ascsi, ide) disk image supplied would be pretty cool
although in that case one would need to count the number of partitions to
guess the proper letter for the supplied command line path.

Now as I think about it, perhaps this is the only way as GEMDOS HD can't
have more than one letter (partition) assigned?

On 28 March 2017 at 12:12, Miro Kropáček <miro.kropacek@xxxxxxxxx> wrote:

Hi,

this is somehow related to my previous email. It would be cool if one
could other boot drive in case "directory | Atari program" is given.

The reason is simple, imagine you have a folder for common setup (NVDI,
some ACCs etc) and you'd like to run the Atari program in *that* environment
automatically.

Same for "directory", sometimes it's nice to boot into given folder with
some preset environment (esp. when testing various binaries).

Basically, only thing needed is to change drive in
{desktop,newdesk,emudesk}.inf from C:\ to D:\ if "-d" is given as C:. It's
totally fine if this fails in case such inf file already exists on C:.

--
MiKRO / Mystic Bytes
http://mikro.atari.org




--
MiKRO / Mystic Bytes
http://mikro.atari.org




--
MiKRO / Mystic Bytes
http://mikro.atari.org




diff -r a2beeb7d7a4a src/includes/tos.h
--- a/src/includes/tos.h	Sun Mar 26 01:09:13 2017 +0200
+++ b/src/includes/tos.h	Wed Mar 29 00:14:03 2017 +0300
@@ -17,7 +17,8 @@
 extern int nNumDrives;
 
 extern void TOS_MemorySnapShot_Capture(bool bSave);
-extern void TOS_AutoStart(const char *prgname);
+extern bool TOS_AutoStart(const char *prgname);
+extern const char *TOS_AutoStartInvalidDrive(void);
 extern FILE *TOS_AutoStartOpen(const char *filename);
 extern bool TOS_AutoStartClose(FILE *fp);
 extern int TOS_LoadImage(void);
diff -r a2beeb7d7a4a src/options.c
--- a/src/options.c	Sun Mar 26 01:09:13 2017 +0200
+++ b/src/options.c	Wed Mar 29 00:14:03 2017 +0300
@@ -64,6 +64,7 @@
 	OPT_CONFIGFILE,
 	OPT_KEYMAPFILE,
 	OPT_FASTFORWARD,
+	OPT_AUTOSTART,
 	OPT_MONO,		/* common display options */
 	OPT_MONITOR,
 	OPT_FULLSCREEN,
@@ -202,6 +203,8 @@
 	  "<file>", "Read (additional) keyboard mappings from <file>" },
 	{ OPT_FASTFORWARD, NULL, "--fast-forward",
 	  "<bool>", "Help skipping stuff on fast machine" },
+	{ OPT_AUTOSTART, NULL, "--auto",
+	  "<x>", "Atari program autostarting with Atari path" },
 
 	{ OPT_HEADER, NULL, NULL, NULL, "Common display" },
 	{ OPT_MONO,      "-m", "--mono",
@@ -867,6 +870,23 @@
 
 
 /**
+ * Do final validation for the earlier + parsed options
+ * 
+ * Return false if they fail validation.
+ */
+static bool Opt_ValidateOptions(void)
+{
+	const char *err;
+
+	if ((err = TOS_AutoStartInvalidDrive()))
+	{
+		return Opt_ShowError(OPT_AUTOSTART, err, "Required autostart drive / GEMDOS HD do are not enabled");
+	}
+	return true;
+}
+
+
+/**
  * Return true if given path points to an Atari program, false otherwise.
  */
 bool Opt_IsAtariProgram(const char *path)
@@ -973,7 +993,7 @@
 	{
 		/* last argument can be a non-option */
 		if (argv[i][0] != '-' && i+1 == argc)
-			return Opt_HandleArgument(argv[i]);
+			return Opt_HandleArgument(argv[i]) && Opt_ValidateOptions();
 
 		/* WhichOption() checks also that there is an argument,
 		 * so we don't need to check that below
@@ -998,6 +1018,13 @@
 			ok = Opt_Bool(argv[++i], OPT_FASTFORWARD, &ConfigureParams.System.bFastForward);
 			break;
 
+		case OPT_AUTOSTART:
+			if (!(ok = TOS_AutoStart(argv[++i])))
+			{
+				return Opt_ShowError(OPT_AUTOSTART, argv[i], "Invalid drive specified for autostart path");
+			}
+			break;
+
 		case OPT_CONFIGFILE:
 			i += 1;
 			/* true -> file needs to exist */
@@ -1496,7 +1523,7 @@
 			if (strlen(str) > 2 && isdigit(str[0]) && str[1] == '=')
 			{
 				drive = str[0] - '0';
-				if (drive < 0 || drive > 7)
+				if (drive < 0 || drive >= MAX_ACSI_DEVS)
 					return Opt_ShowError(OPT_ACSIHDIMAGE, str, "Invalid ACSI drive <id>, must be 0-7");
 				str += 2;
 			}
@@ -2002,7 +2029,7 @@
 			break;
 		       
 		case OPT_BENCHMARK:
-			BenchmarkMode= true;
+			BenchmarkMode = true;
 			break;
 
 		case OPT_ERROR:
@@ -2019,7 +2046,7 @@
 		}
 	}
 
-	return true;
+	return Opt_ValidateOptions();
 }
 
 /**
diff -r a2beeb7d7a4a src/tos.c
--- a/src/tos.c	Sun Mar 26 01:09:13 2017 +0200
+++ b/src/tos.c	Wed Mar 29 00:14:03 2017 +0300
@@ -57,16 +57,14 @@
 
 static struct {
 	FILE *file;          /* file pointer to contents of INF file */
-	char prgname[16];    /* TOS name of the program to auto start */
+	char *prgname;       /* TOS name of the program to auto start */
 	const char *infname; /* name of the INF file TOS will try to match */
-	int match_count;     /* how many times INF was matched after boot */
-	int match_max;       /* how many times TOS needs it to be matched */
 } TosAutoStart;
 
-/* autostarted program name will be added after first '\' character */
+/* autostarted program name will be added befere first '@' character */
 static const char emudesk_inf[] =
 "#E 9A 07\r\n"
-"#Z 01 C:\\@\r\n"
+"#Z 01 @\r\n"
 "#W 00 00 02 06 26 0C 08 C:\\*.*@\r\n"
 "#W 00 00 02 08 26 0C 00 @\r\n"
 "#W 00 00 02 0A 26 0C 00 @\r\n"
@@ -87,7 +85,7 @@
 "#b001000\r\n"
 "#c7770007000600070055200505552220770557075055507703111302\r\n"
 "#d\r\n"
-"#Z 01 C:\\@\r\n"
+"#Z 01 @\r\n"
 "#E D8 11\r\n"
 "#W 00 00 10 01 17 17 13 C:\\*.*@\r\n"
 "#W 00 00 08 0B 1D 0D 00 @\r\n"
@@ -441,10 +439,97 @@
 /**
  * Set name of program that will be auto started after TOS boots.
  * Supported only from TOS 1.04 forward.
+ * 
+ * If program lacks a path, "C:\" will be added.
+ * 
+ * Returns true if OK, false for obviously invalid path specification.
  */
-void TOS_AutoStart(const char *prgname)
+bool TOS_AutoStart(const char *name)
 {
-	Str_Filename2TOSname(prgname, TosAutoStart.prgname);
+	char *prgname;
+	int len = strlen(name);
+	char drive = toupper(name[0]);
+
+	if (drive >= 'A' && drive <= 'Z' && name[1] == ':' && name[2] == '\\')
+	{
+		/* full path */
+		int offset;
+		prgname = malloc(len+1);
+		offset = strrchr(name, '\\') - name + 1;
+		/* copy/upcase path part */
+		memcpy(prgname, name, offset);
+		prgname[offset] = '\0';
+		Str_ToUpper(prgname);
+		/* copy/upcase file part */
+		Str_Filename2TOSname(name+offset, prgname+offset);
+	}
+	else if (strchr(name, '\\'))
+	{
+		/* partial path not accepted */
+		return false;
+	}
+	else
+	{
+		/* just program -> add path */
+		prgname = malloc(3 + len + 1);
+		strcpy(prgname, "C:\\");
+		Str_Filename2TOSname(name, prgname+3);
+	}
+	if (TosAutoStart.prgname)
+		free(TosAutoStart.prgname);
+	TosAutoStart.prgname = prgname;
+	return true;
+}
+
+/*-----------------------------------------------------------------------*/
+/**
+ * Trivial checks on whether autostart program drive may exist.
+ * 
+ * Return NULL if it could, otherwise return the invalid autostart path.
+ */
+const char *TOS_AutoStartInvalidDrive(void)
+{
+	char drive;
+	const char *path = TosAutoStart.prgname;
+
+	if (!path)
+		return NULL;
+	drive = path[0];
+
+	if (!(ConfigureParams.HardDisk.bUseHardDiskDirectories && ConfigureParams.HardDisk.szHardDiskDirectories[0][0]))
+	{
+		Log_Printf(LOG_ERROR, "Autostarting requires GEMDOS HD to be used as boot drive!\n");
+		return path;
+	}
+
+	if (drive == 'A')
+	{
+		if (!(ConfigureParams.DiskImage.EnableDriveA && ConfigureParams.DiskImage.szDiskFileName[0][0]))
+			return path;
+	}
+
+	if (drive == 'B')
+	{
+		if (!(ConfigureParams.DiskImage.EnableDriveB && ConfigureParams.DiskImage.szDiskFileName[1][0]))
+			return path;
+	}
+
+	/* exact drive checking for hard drives would require:
+	 *
+	 * For images:
+	 * - finding out what partitions each of the IDE master &
+	 *   Slave, 8 ACSI, and 8 SCSI images do have, *and*
+	 * - finding out which of those partitions the native Atari
+	 *   harddisk driver happens to support...
+	 * -> not feasible
+	 * 
+	 * For GEMDOS HD:
+	 * - If multiple partitions are specified, which ones
+	 * - If not, what is the single partition drive letter
+	 * 
+	 * So, just return OK...
+	 */
+	return NULL;
 }
 
 /*-----------------------------------------------------------------------*/
@@ -455,7 +540,7 @@
 static void TOS_CreateAutoInf(void)
 {
 	const char *contents, *infname, *prgname;
-	int offset, size, max;
+	int offset, size;
 	FILE *fp;
 #if defined(WIN32)	/* unfortunately tmpfile() needs administrative privileges on windows, so this needs special care */
 	char *ptr;
@@ -466,7 +551,7 @@
 
 	prgname = TosAutoStart.prgname;
 	/* autostart not enabled? */
-	if (!*prgname)
+	if (!prgname)
 		return;
 
 	/* autostart not supported? */
@@ -481,7 +566,6 @@
 		infname = "C:\\EMUDESK.INF";
 		size = sizeof(emudesk_inf);
 		contents = emudesk_inf;
-		max = 1;
 	} else {
 		/* need to match file TOS searches first */
 		if (TosVersion >= 0x0200)
@@ -490,19 +574,16 @@
 			infname = "DESKTOP.INF";
 		size = sizeof(desktop_inf);
 		contents = desktop_inf;
-		max = 1;
 	}
 	/* infname needs to be exactly the same string that given
 	 * TOS version gives for GEMDOS to find.
 	 */
 	TosAutoStart.infname = infname;
-	TosAutoStart.match_max = max;
-	TosAutoStart.match_count = 0;
 
 	/* find where to insert the program name */
-	for (offset = 0; offset < size; )
+	for (offset = 0; offset < size; offset++)
 	{
-		if (contents[offset++] == '\\')
+		if (contents[offset] == '@')
 			break;
 	}
 	assert(offset < size);
@@ -562,17 +643,14 @@
 {
 	if (fp && fp == TosAutoStart.file)
 	{
-		if (++TosAutoStart.match_count >= TosAutoStart.match_max)
-		{
-			/* Remove autostart INF file after TOS has
-			 * read it enough times to do autostarting.
-			 * Otherwise user may try change desktop settings
-			 * and save them, but they would be lost.
-			 */
-			fclose(TosAutoStart.file);
-			TosAutoStart.file = NULL;
-			Log_Printf(LOG_WARN, "Autostart file removed.\n");
-		}
+		/* Remove autostart INF file after TOS has
+		 * read it enough times to do autostarting.
+		 * Otherwise user may try change desktop settings
+		 * and save them, but they would be lost.
+		 */
+		fclose(TosAutoStart.file);
+		TosAutoStart.file = NULL;
+		Log_Printf(LOG_WARN, "Autostart file removed.\n");
 		return true;
 	}
 	return false;


Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/