Why is my string getting trounced?
Hi,
I found a problem with my program that I cannot figure out. I admittedly don't have a good grasp of the scope of variables in spin, so that may be it, but in the below code dstring keeps getting set to what I type in through the getline function. Any help would be appreciated.
I found a problem with my program that I cannot figure out. I admittedly don't have a good grasp of the scope of variables in spin, so that may be it, but in the below code dstring keeps getting set to what I type in through the getline function. Any help would be appreciated.
OBJ
ser : "FullDuplexSerial"
dt : "datatransfer" ' The datatransfer object
key : "combokeyboard"
lcd : "jm_lcd4_ez"
PUB Start | time, okay, ofreq, duty, seconds, period, ontime, offtime, whole, frac, dstring
''Test Parallax Serial Terminal number entry and display.
ser.start(31, 30, 0, 9600)
''start the keyboard
key.start(26)
dira[enable]~~ 'set the enable pin direction (pin 1 on LM293)
''Start the LCD
okay := lcd.init(0, 16, 1)
repeat
ser.tx(13)
dstring := String("0.00")
repeat until ofreq > 99 and ofreq < 50_000_01
ser.str(String("Frequency: "))
lcd.scrollstr(1, 1, 16, 250, @askfreq)
lcd.moveto(12,1)
lcd.cursor(2)
dstring := getline
ser.str(String("Dstring: "))
ser.str(dstring)
ser.dec(StrLen(dstring))
ser.tx(13)
ofreq := StrToFreq(dstring)
ser.str(String("Ofreq: "))
ser.Dec(ofreq)
ser.tx(13)
repeat until duty > 4 and duty < 96
ser.str(String("Duty: "))
lcd.scrollstr(1, 1, 16, 250, @askduty)
lcd.moveto(15,1)
lcd.cursor(2)
duty := StrToDec(getline)
repeat until seconds > 0 and seconds < 601
ser.str(String("Seconds: "))
lcd.scrollstr(1, 1, 16, 250, @asksecs)
lcd.moveto(14,1)
lcd.cursor(2)
''why is dstring getting set to what I type in for duty?
ser.str(String("Dstring: "))
ser.str(dstring)
ser.tx(13)
seconds := StrToDec(getline)
''why is dstring getting set to what I type in for seconds?
ser.str(String("Dstring: "))
ser.str(dstring)
ser.tx(13)
PRI getline | i, c
i := 0
repeat
'repeat while (c := ser.rxcheck) < 0 'use serial
c := key.getkey 'use keyboard
if c == Bsp
if i > 0
ser.tx(8) 'send a real backspace
i--
elseif c == Cr
ser.tx(c) ' If serial console, use CR/LF
ser.tx(Lf)
tline[i] := 0
tp := @tline
return tp
elseif i < linelen-1
ser.tx(c)
lcd.out(c)
tline[i++] := c
PUB StrToDec(stringptr) : value | char, index
'' Converts a zero terminated string representation of a decimal number to a value
value := index := 0
repeat until ((char := byte[stringptr][index++]) == 0)
if char => "0" and char =< "9"
value := value * 10 + (char - "0")
if byte[stringptr] == "-"
value := - value

Comments
Remember that "getline" always returns the address of "tline" where the input line gets stored. Each time you call "getLine", the array "tline" gets used again and changed to whatever you enter.
When you assign "getline" to something else like "dstring", you're only making a copy of the address of the string (in "tline"), not a copy of the string itself.
Assigning the variable, like Mike says, is just copying the address... so in essense, you're overwriting the same memory space for all three instances of where you use it.
If you use something like bytecopy(@ofreq, @dstring, StrSize(@dstring)) you'll get a better result. Don't forget, you'll have to allocate enough space in ofreq to hold the new string, however.
Bill
Attached is the full code. It works great using the serial port and the external numeric keypad.
I'm just trying to get a status screen working on the LCD to finish it up.
http://obex.parallax.com/objects/23/
http://obex.parallax.com/objects/502/
http://obex.parallax.com/objects/529/
$0