![]() |
Forum Index : Microcontroller and PC projects : A beginner (almost), woes aplenty
Page 1 of 2 ![]() ![]() |
|||||
Author | Message | ||||
plover![]() Guru ![]() Joined: 18/04/2013 Location: AustraliaPosts: 306 |
Well, how hard can it be I did learn and use basic decades ago albeit. I am not sure but I seem have stuck in my brain that Geoff Graham may have made a comment like, something about getting a BASIC interpreter up and running in 6 months or was it less, how hard could it be, the plan was laid out. When I saw the thought of ordinary BASIC could be used in real life, Wooow, I had just started looking at these free software development environment, really only some 500 plus MB and I should be able to do something, well there was something about C language and compiling, perhaps wait a little longer. I take heart in that he persevered, the result is history. I have enjoyed following the development immensely. A number of times decided that now I will do it. So far a box full of parts, including a couple of Mick boards actually working (bought them assembled). Do have MMBasic on those boards working using Linux, not to forget Jim's editor, with syntax colouring. You can't let that stay in the box. So while I am doing some AutoTrax crash learning I relax (distract my brain) with running MMBasic in the terminal on Win 7. Running the Basic and having the manual in front of me, cheating by copying the "exercises" from the pdf to the terminal, which has been augmented with some capability in my beloved text editor. Ok, I got to page 9 in the manual, discovered that there was a mistake but found out my manual was too old. It had been corrected in the latest (checked it today) That was good enough for session 1. Started session 2 page 10, Random File IO, which has always bothered me, don't really know why. Here it did become interesting as I had to do some thinking. Well up and running. DOS MMBasic Ver 5.04.08 Copyright 2011-2017 Geoff Graham > OPEN "filename" FOR RANDOM AS #1 Error: No such file or directory > > What? checking back on page 9, naaah fair enough there is no file. Let me put something in the file, saw print statement earlier: > > close 1 > > OPEN "filename.txt" FOR OUTPUT AS #1 > > PRINT #1, "The quick brown Fox jumped over the fence in Daylight to the chookh ouse, but the cockerel would have none of that" > > close 1 Soon found out that I had forgotten that #1 now was open, therefore the CLOSE 1. To my satisfaction and delight I survived the next line, no error message. Quickly a CLOSE 1 just to be sure that would not hit me next with an error. Now of course I have strayed from the manual, but how hard can it be to read something in that file?. Starting to look like cat and mouse, with the mouse laughing > > OPEN "filename.txt" FOR RANDOM AS #1 > dat$ = INPUT$(64, #1) > > print dat$ > > > close 1 To me it seems it did not work, to me it looks like that integer variable dat$ should have had some content, if it does where is it and if not why not. I think I missed something vital about "records" perhaps some declaration might have been smarter? Help please? Oh I see further down the page here comes help. > > close 1 > > RecLen = 64 > OPEN "test.dat" FOR RANDOM AS #1 Error: No such file or directory > DO Error: No matching LOOP > abort: PRINT > PRINT "Number of records in the file =" LOF(#1)/RecLen Number of records in the file = 0 > INPUT "Command (r = read,w = write, a = append, q = quit): ", cmd$ Command (r = read,w = write, a = append, q = quit): IF cmd$ = "q" THEN CLOSE #1 : END > IF cmd$ = "a" THEN Error: No matching ENDIF > SEEK #1, LOF(#1) + 1 > ELSE Error: No matching ENDIF > INPUT "Record Number: ", nbr Record Number: IF nbr < 1 or nbr > LOF(#1)/RecLen THEN PRINT "Invalid record" : GOTO abort > SEEK #1, RecLen * (nbr - 1) + 1 Error: Invalid seek position > ENDIF > IF cmd$ = "r" THEN Error: No matching ENDIF > PRINT "The record = " INPUT$(RecLen, #1) The record = > ELSE Error: No matching ENDIF > LINE INPUT "Enter the data to be written: ", dat$ Enter the data to be written: PRINT #1,dat$ + SPACE$(RecLen - LEN(dat$)); > ENDIF > LOOP Error: LOOP without a matching DO > I think it is time for another day, ![]() |
||||
JohnS Guru ![]() Joined: 18/11/2011 Location: United KingdomPosts: 4044 |
Maybe use the newer V5.04.09 John |
||||
panky![]() Guru ![]() Joined: 02/10/2012 Location: AustraliaPosts: 1115 |
@plover, Looking at your post above, you appear to be entering commands at the MMBasic prompt? For quite a number of the commands you have tried, it makes no sense to enter them at the command prompt and all you will get will be error messages. It might be an idea to download a copy of Geoff's "Getting Started with MMBasic" from his web site and work through the examples in there. Perhaps start with simple 5 or 10 line programs to do things like INPUT to a variable and then output to the console. There are plenty of examples in the manual referenced above. panky ... almost all of the Maximites, the MicromMites, the MM Extremes, the ArmMites, the PicoMite and loving it! |
||||
plover![]() Guru ![]() Joined: 18/04/2013 Location: AustraliaPosts: 306 |
JohnS thanks, very good point, will have to laught here as I went and downloaded today but I only checked the manual. Never occurred to me it would be prudent to just check the version number as well. For some reason my instinct tells me this is not my problem, but my instinct I also often ignore to my peril. Will check in the morning some time. Panky Thanks for replying I did not mention very specificly what manual, but it is inferred that I am diligently going through the manual, page by page. Well I am stepping through the program one line at the time, I did with the examples on p.. 9 and that worked fine??? I may certainly have misunderstood the manual but it seemed logical to me, step through and check it all works? Is it not valid statements? ![]() |
||||
Grogster![]() Admin Group ![]() Joined: 31/12/2012 Location: New ZealandPosts: 9610 |
Hey there. ![]() Most commands CAN be run at the command-prompt in immediate mode, but there are several that CANNOT. Any multi-line command, such as IF/THEN/ELSE will NOT work at the command prompt, unless the interpreter can evaluate the command in one single line. The reason you are getting errors, is that when you press ENTER on your IF/THEN experiments, the interpreter IMMEDIATELY attempts to run that line of code. It does not work, as you are missing the rest of the multi-line statements, and the interpreter has nothing to execute after the THEN keyword, so it falls over with the error about no matching ENDIF. Commands like those ones MUST be run as part of a program code, and they simply can't be run at the command-prompt in immediate mode. EDIT: Well, technically, you CAN do it by separating out the commands using colons. You are still limited to one line of code, but you can do it along the lines of: IF X=1 THEN:PRINT "TRUE":ELSE:PRINT "FALSE":ENDIF That would probably work. Not tested, but it should. EDIT: Just tried it, yes that does work. You really, REALLY need to be entering in the commands using the built-in editor(type EDIT at the command-prompt), so that you can run the code and experiment around. Typing the commands at the prompt like that is a waste of effort too, as the code you are typing will be totally forgotten once the interpreter has executed that line - so you are typing all that code, to have MMBASIC NOT remember it. ![]() I know where you are coming from - entering in the BASIC at the command-prompt. The Atari 800XL I used to have years ago did it that way. Each line was entered at the command prompt, and saved as part of the program. MMBASIC does NOT do it like that. You have to use the built-in editor to write your code, and then use F1 to save it to memory. ![]() Smoke makes things work. When the smoke gets out, it stops! |
||||
plover![]() Guru ![]() Joined: 18/04/2013 Location: AustraliaPosts: 306 |
Grogster Thanks for posting and I like the explanation. I had to try it that way. When I saw the section of code nicely laid out with indents etc, I did think I had better make a file from that and run? In the manual page 6 AUTORUN.BAS is described. Ah, as the previous little exercise by running individual lines turned out to be a big flop. What about copy and paste the "failing" code to the Autorun.bat? In my case simple, I have a file p10-record.bas containing the code ready to test so will make a copy and rename this AUTORUN.BAT Then start up MMBasic.exe from same directory. The following code is next in the manual, reading text in file in reverse order OPEN "file.txt" FOR RANDOM AS #1 FOR i = LOF(#1) TO 1 STEP -1 SEEK #1, i PRINT INPUT$(1, #1); NEXT i CLOSE #1 I can use this to test the file I thought I had made with the Fox and over the fence to the chook house. That exercise ended up with me wondering if there was anything in the file. Named the code file "rev-file.bas" and my code: ' Page 10 in the manual for the MMBasic DOS version ' the file called "rev-file.bas" 'OPEN "file.txt" FOR RANDOM AS #1 'Close #1 'just in case it was open Open "filename.txt" For RANDOM As #1 For i = Lof(#1) To 1 Step -1 Seek #1, i Print Input$(1, #1); Next i Close #1 To get the code into the MMBasic To run the program, F2 [4] Close #1 'just in case it was open Error: File number is not open > Oh, but the filenumber could have been open? How would I know if it is open or not, I tried to outfox the "already open" error. Hmm. EDIT an make the CLOSE #1 line a comment then use F2 key, that is quick and easy taht fo enon evah dluow lerekcoc eht tub ,esuohkoohc eht ot thgilyaD ni ecnef eh t revo depmuj xoF nworb kciuq ehT > Now that was nice, I had managed to fill in some characters in the file, and the new little bit of code also worked. This took a lot longer for me then what I had expected. ZZZzzz.... here |
||||
Grogster![]() Admin Group ![]() Joined: 31/12/2012 Location: New ZealandPosts: 9610 |
I have had that open/close issue myself. IE: How do you know it is open or closed at a certain point. The simplest solution that others on the forums suggested to me at the time, was a flag. I used a variable such as FOF(file open flag), and just tested that before doing any closing of the port. [Code] If FOF then Close #1 FOF=0 'Clear flag Endif Open "FILENAME.TXT" for RANDOM as #1 FOF=1 'Set flag for next time [/Code] This way, as soon as you try to open or close the file, it will first check to find out if the file is already open. If it is, it will close the file first, then re-open it. That kind of thing seems to get around the error that can pop-up when you try to close a file that is not open, or open one that is already opened. Smoke makes things work. When the smoke gets out, it stops! |
||||
TassyJim![]() Guru ![]() Joined: 07/08/2011 Location: AustraliaPosts: 6283 |
Don't use AUTORUN until you are sure the code is working. It can be difficult to escape from rouge programs (and we have them sometimes). Jim VK7JH MMedit |
||||
Geoffg![]() Guru ![]() Joined: 06/06/2011 Location: AustraliaPosts: 3292 |
Or you can use ON ERROR SKIP [Code] On Error Skip Close #1 [/Code] Geoff Graham - http://geoffg.net |
||||
Bill7300 Senior Member ![]() Joined: 05/08/2014 Location: AustraliaPosts: 159 |
Rouge programs, Jim? I usually find it is actually the programmer who ends up with the red face, rather than the program :) Bill Bill |
||||
plover![]() Guru ![]() Joined: 18/04/2013 Location: AustraliaPosts: 306 |
I like the idea of a single line test, can it be made one line such as On Error Skip : Close #1 TassyJim: thanks for the tip about making sure the program runs first. Had not thought about this. Grogster: Later I might just try your flag test out, as a single liner. General: In a big program I assume then that there is no way of knowing how many file numbers are in use. The follow on then is that make sure you keep tight control over what the file numbers up to, be diligent if used make sure they get closed quickly? |
||||
rave Newbie ![]() Joined: 24/02/2018 Location: United StatesPosts: 28 |
Makes a lot of sense. When the program terminates normally (or abnormally) you would want the file/stream to be closed and that can be easily resolved by checking the program's state depending on the program logic (e.g. using a global flag) which is better than ignoring all IO errors just to do a CLOSE #1. Maybe I'm dumb to understand, but I don't see why one needs a CLOSE #1 before an OPEN #1. The BASIC dialects that I am familiar with close the file/stream before opening a new file/stream with the same number. For example, SuperBASIC (used with my 2 Sinclair QLs, now collecting dust) says: "The OPEN command will close a channel which is already open with the same channel number prior to opening the new channel" http://superbasic-manual.readthedocs.io/en/latest/KeywordsO.clean.html#open So there should not be a need to CLOSE #1 before an OPEN #1 when there is any doubt whether or not #1 is still open. Why would this be any different in MMBASIC? - Rob |
||||
Grogster![]() Admin Group ![]() Joined: 31/12/2012 Location: New ZealandPosts: 9610 |
I don't think MMBASIC does that. The channel is left open till the program explicitly closes it. Perhaps that is something worthy of change. Geoff? Smoke makes things work. When the smoke gets out, it stops! |
||||
Geoffg![]() Guru ![]() Joined: 06/06/2011 Location: AustraliaPosts: 3292 |
Well, the correct way to handle a file is to open it, transfer data then close it. You could have an automatic close on the next open and save typing in one command (Close #x) but then you would have no warning if you accidentally misused a file number. I have never heard of this automatic close before, I suspect Sinclair was on their own with that one. Geoff Graham - http://geoffg.net |
||||
plover![]() Guru ![]() Joined: 18/04/2013 Location: AustraliaPosts: 306 |
So it is a matter of keeping careful count on closing filenumber as soon as one has opened it. I will try. In the manual p.4 I pondered the DOS MMBasic variables, decided to try and print them with following statements, they do look innocent I am testing them one by one, I copy and paste: ? MM.CMDLINE$ ? MM.VRES ? MM.HRES In the bassic terminal window > ? MM.CMDLINE$ > > ? MM.VRES 24 > > ? MM.HRES 79 > The two last ones seem ok but what about MM.CMDLINES An empty line?? Looks I am in trouble again? |
||||
Grogster![]() Admin Group ![]() Joined: 31/12/2012 Location: New ZealandPosts: 9610 |
I have never heard of this automatic close before, I suspect Sinclair was on their own with that one. I agree with that. I have never heard of auto-close either. You might have been right there about Clive! ![]() Even thirty years ago when I was writing BASIC for my Atari, you had to CLOSE a file you had OPEN'ed. It was left up to the programmer to close the file. .....and that was in 8-bit BASIC from 35 years ago.... Smoke makes things work. When the smoke gets out, it stops! |
||||
plover![]() Guru ![]() Joined: 18/04/2013 Location: AustraliaPosts: 306 |
I have moved back to about p.4 in the manual, looking at environment variables, interesting because I am outdone from the start, bit of the manual, split it up abit in my exercise book, the quote from my boo: Windows environment variables can be used to change some characteristics of MMBasic. MMDIR can be set to the default directory that MMBasic is to start running in. For example: SET MMDIR=C:\Temp will start MMBasic running in the directory C:\Temp. Without this the starting directory will be specified by the operating system and will vary depending on how MMBasic is started. The directory path must be quoted if it includes spaces. eg: SET MMDIR="C:\Program Files" Following path line is where I have my running mmbasic.exe located and files as created etc. Presently this is where mmbasix.exe will run in that location. SET MMDIR=C:\Users\Aurak\Downloads\180630-MMBasic-DOS\DOS_MMBasic\ So the test, I am going to try and get MMBasic to run in the parent directory, or one level back up the chain. As I understand done by setting env variable: SET MMDIR=C:\Users\Aurak\Downloads\180630-MMBasic-DOS\ Done, then I check in the MMBasic terminal window with the "files" statement: The files showing tells me that is the original location I started in tonight, but I expected to see the file in the parent directory?? I think I did restart, MMBasic from original location again, after I had caried out the SET MMDIR=... but at the same time I happened to read agin that the path should be quoated,@#$%, i have to repeat quotes SET MMDIR="C:\Users\Aurak\Downloads\180630-MMBasic-DOS\" Actually tried to put red colours around the " mark, that is no go. SET path including the quotes. Then the make sure I had closed the MMBasic terminal window I then started it up again. Do the "files" test: What, ![]() Well making great progress here going backwards it seems. This is the way to learn I know but one does get a weeny bit tempted skip these basic things perhaps. As this is run under windows 764 I am qurious where can I check the ENV list settings, in Linux with a bit of luck I can run a long list and actually see what the values are that are assigned. Has MMDIR been assigned a value? I was hoping that running the "files" in the MMBasic terminal would have shown the parent directory (notice the "files" run result does show a path line. Somebody drag me out the quicksand before it is too late. |
||||
flip Senior Member ![]() Joined: 18/07/2016 Location: AustraliaPosts: 114 |
Hi plover, Out of interest are you setting the MMDIR globally? One way to check from within MM environment typing 2 commands in bold as follows: DOS MMBasic Ver 5.04.09 From above you can see even though quotes not required (and are mangled by Windows) the behaviour is OKCopyright 2011-2018 Geoff Graham > system "set" ALLUSERSPROFILE=C:\ProgramData APPDATA=C:\Users\phil\AppData\Roaming ... mmdir=C:\users\phil" ... windir=C:\WINDOWS > files Volume in drive C is Windows Volume Serial Number is 764F-B060 Directory of C:\Users\phil ... > If you can't see MMDIR then need to set it in same session as you run MMBASIC, OR set it using Admin settings. Start...Right-Click on My Computer...Properties...Advanced System Settings...Environment Variables..and add it there. This is probably the best way if you want it permanently set to the same folder. I don't use this personally as I find it too restrictive, but that's just me. Aside from this, I can see you have AUTORUN.BAS in the directory. it may be that there are some commands in here that are changing your current directory which might be overriding any environment variable.(I am not 100% sure on this as it may dependent how you are starting MMBASIC...but if ENV setting MMDIR wasn't your problem, you could try temporarily renaming AUTORUN.BAS to something else and try it) Regards, Phil |
||||
plover![]() Guru ![]() Joined: 18/04/2013 Location: AustraliaPosts: 306 |
flip Wooww, better than I hoped for, the list of env variables. I am going to attach terminal picture, but I see my thinking about how to verify if MMDIR was set, was good idea. From the list it is not set. My thought was setting the env in a Windows terminal that might make it Global, obviously that has failed and as I accidentally also set it in root/admin terminal this did not do the trick either (nothing showing). Your pathway to set the env variable, seems like hard work and it does not appeal to me as I will have forgotten in 3 days how I got there but might remember it was described here. Assume I will find out later if and what may be needed. Add to this I don't know if I need to use it, not clear to me. I am just at the moment battling my way through the manual hoping something will stick in my head. So locally you SET in MMBasic, and globally you take the tourist path via Windows. Then to check back into MMBasic and run the "system "SET"" and files. |
||||
flip Senior Member ![]() Joined: 18/07/2016 Location: AustraliaPosts: 114 |
hey plover Just a note on the global environment setting - it's permanent, so you wouldn't need to remember the procedure (and its handy knowledge for Windows). Also note the example with the SYSTEM "SET" command you can run any OS command-see MMBASIC for DOS manual, and also type help at DOS prompt (or system "help" from MMBASIC) And also note in your program you can also force directory change e.g. > system "CD" These all work not only in 'command mode' but in 'run mode' so you have complete control either way.C:\Users\phil\Apps\MMBasic\DEV\MMDB\AppBuilder\APT > chdir ".." > system "CD" C:\Users\phil\Apps\MMBasic\DEV\MMDB\AppBuilder > Note all the following options are able to invoke MMBASIC from the directory you're program is in (which I think may be most useful) - MMEDIT from Jim Hiley which you can invoke MMBASIC directly from a toolbar button - Notepad++ which gives a roughly compatible (VB language) editor from which you can set the program to run from the menu (just takes a bit of mucking around to setup) - Windows associate .BAS file with your MMBASIC.exe...Again this is a once-off setting, and will invoke MMBASIC in whatever current director you have File Explorer open in, just by double-clicking the .BAS file - AUTORUN.BAS which you had on your system (see manual-this file depends on Windows paths). Once successfully invoked you can include commands like above 'CHDIR'-see MMBASIC for DOS manual. The best thing I can suggest is until you fully understand exact behaviour... as I get bitten by Murphy too often always ![]() EDIT just notice you got Geoff Graham's demo Simple DB program running - so all good - until next problem !!...happy tinkering! Regards Phil |
||||
Page 1 of 2 ![]() ![]() |
![]() |
![]() |
The Back Shed's forum code is written, and hosted, in Australia. | © JAQ Software 2025 |