Can any one help

Started by ITand RD, ICL Ltd June 23, 2003
I have two tasks:

1) One to report a temperature and send a message out of Comm3,
2) To detect when a switch is pressed and send a message out of Comm3.

Individually these tasks work perfectly. However, when put together under multitasking, nothing would work.

Source code is as below.

Grateful id anyone could advise.

Big Thanks.

prakash

Code:

Option Explicit
Dim Com3_Out(1 To 40) As Byte 'Com3 Out Buffer
Dim Com3_In(1 To 40) As Byte 'Com3 In Buffer

Const A_THERMISTOR as Single = 0.000623 ' Thermistor two-point model used to
calculate Temperature
Const B_THERMISTOR as single = 0.000297

Public inMSg as string

Const InputPin As Byte = 17

Const ButtonPressed As Byte = 1
Const ButtonReleased As Byte = 0

Dim StackReadTemperature(1 To 30) As Byte
Dim StackReadButtonPress(1 To 30) As Byte

Public Sub Main()

Call OpenQueue(Com3_Out, 40)
Call OpenQueue(Com3_In, 40)
'Define pins for Com3 (RX = pin13, TX= pin14)
Call DefineCom3(13, 14, bx1000_1000)
Call OpenCom(3,9600, Com3_In, Com3_Out)

Call PutPin(InputPin, bxInputTristate)

CallTask "ReadTemperatureTask", StackReadTemperature
CallTask "ReadButtonPressTask", StackReadButtonPress

do
call sleep(1.0)
loop

End Sub sub ReadTemperatureTask()
dim inCounter as integer
Dim Rtherm as Single, TK as Single, TC as Single, TF as Single

dim Hour as Byte, Minute as Byte, Second as single
dim Year as integer, Month as Byte, Day as Byte
dim strDateTime as string

do
TF = MeasTemp()
Call GetTimestamp(Year, Month, Day, Hour, Minute, Second)
strDateTime = cstr(Day) & "/" & cstr(Month) & "/" & cstr(Year)
strDateTime = strDateTime & " " & cstr(Hour) & ":" & cstr(Minute)

strDateTime = strDateTime & " " & cstr(TF)

call SendMessage(strDateTime)

call sleep(0.5)

loop
end sub

sub ReadButtonPressTask()
dim strMsg as string
dim State as Byte

state = 0

Do
LockTask
' Toggle State if button is pressed.
If (GetPin(InputPin) = ButtonPressed) Then

State = State Xor 1
' Pause 0.1 s for button de-bounce.
strMsg = "Button Pressed"
call SendMessage(strMsg )
Call Delay(1.0)

' Wait for release.
Do Until (GetPin(InputPin) = ButtonReleased)
state = state Xor 1
Loop
End If
unlockTask
call sleep(0.5)

loop

end sub

private sub SendMessage(strMsg as string)
dim inCounter as integer

strMsg = ">STX" & strMsg
'for incounter = 1 to 2
Call PutQueueStr(Com3_Out, strMsg )
debug.print strMsg
'next End Sub

Function MeasTemp() as Single

Dim ADVal as Integer
Dim Rtherm as Single, TK as Single, TC as Single, TF as Single

ADVal = GetADC(16) ' A/D conversion
Rtherm = 10000.0/((1024.0/CSng(ADVal))-1.0) ' Calculate thermistor R
TK = 1.0/(A_THERMISTOR + B_THERMISTOR *log(Rtherm)) ' T_Kelvin
TC = TK-273.15 ' T_Celcius
TF = (TC * 1.8) + 32.0 ' T_Fahr
'MeasTemp = TF
MeasTemp = TC End Function



Hi Prakash!

After only a quick look at your code, I suspect that by using a two queues,
and sending out of comm3 from your Main, you will solve the problem.

If you create a queue for each task, and then have the main loop look at the
queues seperatly, sending only when there is something in the queue, you
will solve your problem. I would also suggest two "data good" variables that
are only set after the entire message is placed into the queue. By changing
the delay in your main loop, you can control the latency of the data sent.

Sloan

----- Original Message -----
From: "ITand RD, ICL Ltd" <>
To: <>
Cc: "S Sharma ICL Ltd" <>
Sent: Monday, June 23, 2003 8:41 AM
Subject: [BasicX] Can any one help > I have two tasks:
>
> 1) One to report a temperature and send a message out of Comm3,
> 2) To detect when a switch is pressed and send a message out of Comm3.
>
> Individually these tasks work perfectly. > However, when put together under multitasking, nothing would work.
>
> Source code is as below.
>
> Grateful id anyone could advise.
>
> Big Thanks.
>
> prakash
>
> Code:
>
> Option Explicit
> Dim Com3_Out(1 To 40) As Byte 'Com3 Out Buffer
> Dim Com3_In(1 To 40) As Byte 'Com3 In Buffer
>
> Const A_THERMISTOR as Single = 0.000623 ' Thermistor two-point model used
to
> calculate Temperature
> Const B_THERMISTOR as single = 0.000297
>
> Public inMSg as string
>
> Const InputPin As Byte = 17
>
> Const ButtonPressed As Byte = 1
> Const ButtonReleased As Byte = 0
>
> Dim StackReadTemperature(1 To 30) As Byte
> Dim StackReadButtonPress(1 To 30) As Byte >
>
> Public Sub Main()
>
> Call OpenQueue(Com3_Out, 40)
> Call OpenQueue(Com3_In, 40)
> 'Define pins for Com3 (RX = pin13, TX= pin14)
> Call DefineCom3(13, 14, bx1000_1000)
> Call OpenCom(3,9600, Com3_In, Com3_Out)
>
> Call PutPin(InputPin, bxInputTristate)
>
> CallTask "ReadTemperatureTask", StackReadTemperature
> CallTask "ReadButtonPressTask", StackReadButtonPress
>
> do
> call sleep(1.0)
> loop >
>
> End Sub > sub ReadTemperatureTask()
> dim inCounter as integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single
>
> dim Hour as Byte, Minute as Byte, Second as single
> dim Year as integer, Month as Byte, Day as Byte
> dim strDateTime as string
>
> do
> TF = MeasTemp()
> Call GetTimestamp(Year, Month, Day, Hour, Minute, Second)
> strDateTime = cstr(Day) & "/" & cstr(Month) & "/" & cstr(Year)
> strDateTime = strDateTime & " " & cstr(Hour) & ":" & cstr(Minute)
>
> strDateTime = strDateTime & " " & cstr(TF)
>
> call SendMessage(strDateTime)
>
> call sleep(0.5)
>
> loop >
> end sub
>
> sub ReadButtonPressTask()
> dim strMsg as string
> dim State as Byte
>
> state = 0
>
> Do
> LockTask
> ' Toggle State if button is pressed.
> If (GetPin(InputPin) = ButtonPressed) Then
>
> State = State Xor 1 >
> ' Pause 0.1 s for button de-bounce.
> strMsg = "Button Pressed"
> call SendMessage(strMsg )
> Call Delay(1.0)
>
> ' Wait for release.
> Do Until (GetPin(InputPin) = ButtonReleased)
> state = state Xor 1
> Loop
> End If
> unlockTask
> call sleep(0.5)
>
> loop >
>
> end sub
>
> private sub SendMessage(strMsg as string)
> dim inCounter as integer
>
> strMsg = ">STX" & strMsg
> 'for incounter = 1 to 2
> Call PutQueueStr(Com3_Out, strMsg )
> debug.print strMsg
> 'next > End Sub
>
> Function MeasTemp() as Single
>
> Dim ADVal as Integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single >
>
> ADVal = GetADC(16) ' A/D conversion
> Rtherm = 10000.0/((1024.0/CSng(ADVal))-1.0) ' Calculate thermistor R
> TK = 1.0/(A_THERMISTOR + B_THERMISTOR *log(Rtherm)) ' T_Kelvin
> TC = TK-273.15 ' T_Celcius
> TF = (TC * 1.8) + 32.0 ' T_Fahr
> 'MeasTemp = TF
> MeasTemp = TC > End Function >
> ">http://docs.yahoo.com/info/terms/ >




My guess would be that your stack sizes are too small for the tasks.
I would also guess that you have oodles of available ram so try
dimming your stacks at a generous 1 TO 100 and you'll probably see
your code work.

Frank and others have posted methods in finding out exactly how much
stack space is required for your tasks... you can find those with a
search on the board here. Those methods also require that your code
work first :-)

Initially, when writing a program like this, I give tasks lots more
stack then they probably need and when i'm "more or less" finished
with my programming, then I find out how much stack space is actually
required. Adding / removing code from your tasks changes it's stack
requirements which is why I never really worry about "how much
exactly is needed" until I'm pretty much done with revisions.

Also, I see that you have 31 bytes each for COM3 input / output
buffer. If the COM3 input buffer should get over-run... it is
possible that COM3 input data can trash the memory areas dimmed for
stack (just a note). Stack space is always mapped at the end of your
other dimmed variables... so COM3 input buffer being mapped just
before it could trash the stack area if overflowed. --- In , "ITand RD, ICL Ltd" <it-and-RD@i...>
wrote:
> I have two tasks:
>
> 1) One to report a temperature and send a message out of Comm3,
> 2) To detect when a switch is pressed and send a message out of
Comm3.
>
> Individually these tasks work perfectly. > However, when put together under multitasking, nothing would work.
>
> Source code is as below.
>
> Grateful id anyone could advise.
>
> Big Thanks.
>
> prakash
>
> Code:
>
> Option Explicit
> Dim Com3_Out(1 To 40) As Byte 'Com3 Out Buffer
> Dim Com3_In(1 To 40) As Byte 'Com3 In Buffer
>
> Const A_THERMISTOR as Single = 0.000623 ' Thermistor two-
point model used to
> calculate Temperature
> Const B_THERMISTOR as single = 0.000297
>
> Public inMSg as string
>
> Const InputPin As Byte = 17
>
> Const ButtonPressed As Byte = 1
> Const ButtonReleased As Byte = 0
>
> Dim StackReadTemperature(1 To 30) As Byte
> Dim StackReadButtonPress(1 To 30) As Byte >
>
> Public Sub Main()
>
> Call OpenQueue(Com3_Out, 40)
> Call OpenQueue(Com3_In, 40)
> 'Define pins for Com3 (RX = pin13, TX= pin14)
> Call DefineCom3(13, 14, bx1000_1000)
> Call OpenCom(3,9600, Com3_In, Com3_Out)
>
> Call PutPin(InputPin, bxInputTristate)
>
> CallTask "ReadTemperatureTask", StackReadTemperature
> CallTask "ReadButtonPressTask", StackReadButtonPress
>
> do
> call sleep(1.0)
> loop >
>
> End Sub > sub ReadTemperatureTask()
> dim inCounter as integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single
>
> dim Hour as Byte, Minute as Byte, Second as single
> dim Year as integer, Month as Byte, Day as Byte
> dim strDateTime as string
>
> do
> TF = MeasTemp()
> Call GetTimestamp(Year, Month, Day, Hour, Minute, Second)
> strDateTime = cstr(Day) & "/" & cstr(Month) & "/" & cstr(Year)
> strDateTime = strDateTime & " " & cstr(Hour) & ":" & cstr
(Minute)
>
> strDateTime = strDateTime & " " & cstr(TF)
>
> call SendMessage(strDateTime)
>
> call sleep(0.5)
>
> loop >
> end sub
>
> sub ReadButtonPressTask()
> dim strMsg as string
> dim State as Byte
>
> state = 0
>
> Do
> LockTask
> ' Toggle State if button is pressed.
> If (GetPin(InputPin) = ButtonPressed) Then
>
> State = State Xor 1 >
> ' Pause 0.1 s for button de-bounce.
> strMsg = "Button Pressed"
> call SendMessage(strMsg )
> Call Delay(1.0)
>
> ' Wait for release.
> Do Until (GetPin(InputPin) = ButtonReleased)
> state = state Xor 1
> Loop
> End If
> unlockTask
> call sleep(0.5)
>
> loop >
>
> end sub
>
> private sub SendMessage(strMsg as string)
> dim inCounter as integer
>
> strMsg = ">STX" & strMsg
> 'for incounter = 1 to 2
> Call PutQueueStr(Com3_Out, strMsg )
> debug.print strMsg
> 'next > End Sub
>
> Function MeasTemp() as Single
>
> Dim ADVal as Integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single >
>
> ADVal = GetADC(16) ' A/D conversion
> Rtherm = 10000.0/((1024.0/CSng(ADVal))-1.0) '
Calculate thermistor R
> TK = 1.0/(A_THERMISTOR + B_THERMISTOR *log(Rtherm)) '
T_Kelvin
> TC = TK-273.15 ' T_Celcius
> TF = (TC * 1.8) + 32.0 ' T_Fahr
> 'MeasTemp = TF
> MeasTemp = TC > End Function




how about making the variables global and not redeclaring them ... thats how I ran two tasks, but I had the same problem, smashing the tasks when running 3 or more. I had three tasks about the same size and had to split the program into two microcontrollers. Two tasks in one controller and one in the other. I did not have problems with the two task version but I did not redeclare the variables every time it ran.

T
----- Original Message -----
From: Sloan Thrasher
To:
Sent: Monday, June 23, 2003 12:14 PM
Subject: Re: [BasicX] Can any one help Hi Prakash!

After only a quick look at your code, I suspect that by using a two queues,
and sending out of comm3 from your Main, you will solve the problem.

If you create a queue for each task, and then have the main loop look at the
queues seperatly, sending only when there is something in the queue, you
will solve your problem. I would also suggest two "data good" variables that
are only set after the entire message is placed into the queue. By changing
the delay in your main loop, you can control the latency of the data sent.

Sloan

----- Original Message -----
From: "ITand RD, ICL Ltd" <>
To: <>
Cc: "S Sharma ICL Ltd" <>
Sent: Monday, June 23, 2003 8:41 AM
Subject: [BasicX] Can any one help > I have two tasks:
>
> 1) One to report a temperature and send a message out of Comm3,
> 2) To detect when a switch is pressed and send a message out of Comm3.
>
> Individually these tasks work perfectly. > However, when put together under multitasking, nothing would work.
>
> Source code is as below.
>
> Grateful id anyone could advise.
>
> Big Thanks.
>
> prakash
>
> Code:
>
> Option Explicit
> Dim Com3_Out(1 To 40) As Byte 'Com3 Out Buffer
> Dim Com3_In(1 To 40) As Byte 'Com3 In Buffer
>
> Const A_THERMISTOR as Single = 0.000623 ' Thermistor two-point model used
to
> calculate Temperature
> Const B_THERMISTOR as single = 0.000297
>
> Public inMSg as string
>
> Const InputPin As Byte = 17
>
> Const ButtonPressed As Byte = 1
> Const ButtonReleased As Byte = 0
>
> Dim StackReadTemperature(1 To 30) As Byte
> Dim StackReadButtonPress(1 To 30) As Byte >
>
> Public Sub Main()
>
> Call OpenQueue(Com3_Out, 40)
> Call OpenQueue(Com3_In, 40)
> 'Define pins for Com3 (RX = pin13, TX= pin14)
> Call DefineCom3(13, 14, bx1000_1000)
> Call OpenCom(3,9600, Com3_In, Com3_Out)
>
> Call PutPin(InputPin, bxInputTristate)
>
> CallTask "ReadTemperatureTask", StackReadTemperature
> CallTask "ReadButtonPressTask", StackReadButtonPress
>
> do
> call sleep(1.0)
> loop >
>
> End Sub > sub ReadTemperatureTask()
> dim inCounter as integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single
>
> dim Hour as Byte, Minute as Byte, Second as single
> dim Year as integer, Month as Byte, Day as Byte
> dim strDateTime as string
>
> do
> TF = MeasTemp()
> Call GetTimestamp(Year, Month, Day, Hour, Minute, Second)
> strDateTime = cstr(Day) & "/" & cstr(Month) & "/" & cstr(Year)
> strDateTime = strDateTime & " " & cstr(Hour) & ":" & cstr(Minute)
>
> strDateTime = strDateTime & " " & cstr(TF)
>
> call SendMessage(strDateTime)
>
> call sleep(0.5)
>
> loop >
> end sub
>
> sub ReadButtonPressTask()
> dim strMsg as string
> dim State as Byte
>
> state = 0
>
> Do
> LockTask
> ' Toggle State if button is pressed.
> If (GetPin(InputPin) = ButtonPressed) Then
>
> State = State Xor 1 >
> ' Pause 0.1 s for button de-bounce.
> strMsg = "Button Pressed"
> call SendMessage(strMsg )
> Call Delay(1.0)
>
> ' Wait for release.
> Do Until (GetPin(InputPin) = ButtonReleased)
> state = state Xor 1
> Loop
> End If
> unlockTask
> call sleep(0.5)
>
> loop >
>
> end sub
>
> private sub SendMessage(strMsg as string)
> dim inCounter as integer
>
> strMsg = ">STX" & strMsg
> 'for incounter = 1 to 2
> Call PutQueueStr(Com3_Out, strMsg )
> debug.print strMsg
> 'next > End Sub
>
> Function MeasTemp() as Single
>
> Dim ADVal as Integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single >
>
> ADVal = GetADC(16) ' A/D conversion
> Rtherm = 10000.0/((1024.0/CSng(ADVal))-1.0) ' Calculate thermistor R
> TK = 1.0/(A_THERMISTOR + B_THERMISTOR *log(Rtherm)) ' T_Kelvin
> TC = TK-273.15 ' T_Celcius
> TF = (TC * 1.8) + 32.0 ' T_Fahr
> 'MeasTemp = TF
> MeasTemp = TC > End Function >
> ">http://docs.yahoo.com/info/terms/ >



From: Timber Wolfe <>

> how about making the variables global and not
> redeclaring them [...]

That does have the advantage of reducing the stack required by the
temperature task and button tasks.

On the other hand, that takes memory away from the main stack.
Also, by making variables static rather than local, that memory is
tied up permanently for the life of the program. So that may
actually make the problem worse.

-- Frank Manning
-- NetMedia, Inc.


well if its the only thing the computer is doing (he gave us the code) does it matter if its permanant or not?

This worked in my program too ... does the computer recreate the variables or does it keep them in their own memory segment until they are destroyed or what? (how does it handle it?) ----- Original Message -----
From: Frank Manning
To:
Sent: Monday, June 23, 2003 12:59 PM
Subject: Re: [BasicX] Can any one help From: Timber Wolfe <>

> how about making the variables global and not
> redeclaring them [...]

That does have the advantage of reducing the stack required by the
temperature task and button tasks.

On the other hand, that takes memory away from the main stack.
Also, by making variables static rather than local, that memory is
tied up permanently for the life of the program. So that may
actually make the problem worse.

-- Frank Manning
-- NetMedia, Inc.



Frank,

I just told my partner about this (we have been trying to find a way to do it "our program" with one controller) and he got excited about it again and was reading the posts. He said I sounded like I was being cocky. I am just letting you know I did not mean that cocky or mean or anything was just asking how it "should" be done. We have been working on this stack crashing problem for a long time.

Also:
In the manual regarding the processes I read that you had tested it running something around 1000 processes ... what was that code doing? Can we see what that code was?

Thanks,
Timber ----- Original Message -----
From: Timber Wolfe
To:
Sent: Monday, June 23, 2003 1:07 PM
Subject: Re: [BasicX] Can any one help well if its the only thing the computer is doing (he gave us the code) does it matter if its permanant or not?

This worked in my program too ... does the computer recreate the variables or does it keep them in their own memory segment until they are destroyed or what? (how does it handle it?) ----- Original Message -----
From: Frank Manning
To:
Sent: Monday, June 23, 2003 12:59 PM
Subject: Re: [BasicX] Can any one help From: Timber Wolfe <>

> how about making the variables global and not
> redeclaring them [...]

That does have the advantage of reducing the stack required by the
temperature task and button tasks.

On the other hand, that takes memory away from the main stack.
Also, by making variables static rather than local, that memory is
tied up permanently for the life of the program. So that may
actually make the problem worse.

-- Frank Manning
-- NetMedia, Inc.


From: Timber Wolfe <>

> From: Frank Manning:
> [...]
>> Also, by making variables static rather than local,
>> that memory is tied up permanently for the life of
>> the program. So that may actually make the problem
>> worse. [...]
>
> well if its the only thing the computer is doing (he
> gave us the code) does it matter if its permanant or
> not? [...]

Good question.

It might be easier to explain if we look at a simple example.

Suppose we need to find the standard deviation of 300 samples of 8
bit ADC data on one channel. Also suppose we need to do the same
thing for 150 samples of 10 bit ADC data on another channel.

Also assume that all data for one channel needs to be in memory at
the same time, but we need only one channel at a time. That is,
both channels don't need to be in memory simultaneously.

We can store the 8 bit data in 300 bytes. The 10 bit data also
requires 300 bytes, at 2 bytes per sample.

Right away we can see a problem -- we need at least 600 bytes of
storage, but the BX-24 has only 401 bytes of RAM.

An example program is shown below, where the samples are stored in
global variables as is fashionable on this forum. But the program
won't compile because it overflows RAM.

Is there another way of solving the problem, without increasing
RAM and without changing the algorithm for finding standard
deviation?

-- Frank Manning
-- NetMedia, Inc.

'------------------------
Option Explicit

Public Const LoResCount As Integer = 300
Public Const HiResCount As Integer = 150

Public LoRes(1 To LoResCount) As Byte
Public HiRes(1 To HiResCount) As Integer
'------------------------
Public Sub Main()

Dim L As Single
Dim H As Single

L = LoResStdDev

Debug.Print "LoRes standard deviation: "; CStr(L)

H = HiResStdDev

Debug.Print "HiRes standard deviation: "; CStr(H)

End Sub
'------------------------
Public Function LoResStdDev() As Single

' Returns the standard deviation of 300 samples of ADC data.
' The data consists of 8 bit samples from ADC pin 19. The
' sample rate is 512 samples per second.

Dim N As Integer
Dim Average As Single
Dim SumSquare As Single
Dim Residual As Single
Dim Variance As Single
Const Scale As Single = 255.0
Const Pin As Byte = 19

Average = 0.0
For N = 1 To LoResCount
Call DelayUntilClockTick
LoRes(N) = CByte(GetADC(Pin) \ 4) ' Reduce 2 bits.
Average = Average + (CSng(LoRes(N)) / Scale)
Next
Average = Average / CSng(LoResCount)

SumSquare = 0.0
For N = 1 To LoResCount
Residual = (CSng(LoRes(N)) / Scale) - Average
SumSquare = SumSquare + (Residual * Residual)
Next

Variance = SumSquare / CSng(LoResCount - 1)
LoResStdDev = Sqr(Variance)

End Function
'------------------------
Public Function HiResStdDev() As Single

' Returns the standard deviation of 150 samples of ADC data.
' The data consists of 10 bit samples from ADC pin 20. The
' sample rate is 512 samples per second.

Dim N As Integer
Dim Average As Single
Dim SumSquare As Single
Dim Residual As Single
Dim Variance As Single
Const Scale As Single = 1023.0
Const Pin As Byte = 19

Average = 0.0
For N = 1 To HiResCount
Call DelayUntilClockTick
HiRes(N) = GetADC(Pin)
Average = Average + (CSng(HiRes(N)) / Scale)
Next
Average = Average / CSng(HiResCount)

SumSquare = 0.0
For N = 1 To HiResCount
Residual = (CSng(HiRes(N)) / Scale) - Average
SumSquare = SumSquare + (Residual * Residual)
Next

Variance = SumSquare / CSng(HiResCount - 1)
HiResStdDev = Sqr(Variance)

End Function
'------------------------



If I were doing this program I would not use the multitasking.
Put the read ADC and the Read Keypress between a Do and Loop only.
I am reading 3 Joysticks and controlling 7 servos that way with no
problems and also saving the last position from each servo to compare
the reading with the new one. If its the same I do notsend it to the
serial port but go to the next Joystick location.
I have had problems with the multitasking and do not use it.
--- In , "ITand RD, ICL Ltd" <it-and-RD@i...>
wrote:
> I have two tasks:
>
> 1) One to report a temperature and send a message out of Comm3,
> 2) To detect when a switch is pressed and send a message out of
Comm3.
>
> Individually these tasks work perfectly. > However, when put together under multitasking, nothing would work.
>
> Source code is as below.
>
> Grateful id anyone could advise.
>
> Big Thanks.
>
> prakash
>
> Code:
>
> Option Explicit
> Dim Com3_Out(1 To 40) As Byte 'Com3 Out Buffer
> Dim Com3_In(1 To 40) As Byte 'Com3 In Buffer
>
> Const A_THERMISTOR as Single = 0.000623 ' Thermistor two-
point model used to
> calculate Temperature
> Const B_THERMISTOR as single = 0.000297
>
> Public inMSg as string
>
> Const InputPin As Byte = 17
>
> Const ButtonPressed As Byte = 1
> Const ButtonReleased As Byte = 0
>
> Dim StackReadTemperature(1 To 30) As Byte
> Dim StackReadButtonPress(1 To 30) As Byte >
>
> Public Sub Main()
>
> Call OpenQueue(Com3_Out, 40)
> Call OpenQueue(Com3_In, 40)
> 'Define pins for Com3 (RX = pin13, TX= pin14)
> Call DefineCom3(13, 14, bx1000_1000)
> Call OpenCom(3,9600, Com3_In, Com3_Out)
>
> Call PutPin(InputPin, bxInputTristate)
>
> CallTask "ReadTemperatureTask", StackReadTemperature
> CallTask "ReadButtonPressTask", StackReadButtonPress
>
> do
> call sleep(1.0)
> loop >
>
> End Sub > sub ReadTemperatureTask()
> dim inCounter as integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single
>
> dim Hour as Byte, Minute as Byte, Second as single
> dim Year as integer, Month as Byte, Day as Byte
> dim strDateTime as string
>
> do
> TF = MeasTemp()
> Call GetTimestamp(Year, Month, Day, Hour, Minute, Second)
> strDateTime = cstr(Day) & "/" & cstr(Month) & "/" & cstr(Year)
> strDateTime = strDateTime & " " & cstr(Hour) & ":" & cstr
(Minute)
>
> strDateTime = strDateTime & " " & cstr(TF)
>
> call SendMessage(strDateTime)
>
> call sleep(0.5)
>
> loop >
> end sub
>
> sub ReadButtonPressTask()
> dim strMsg as string
> dim State as Byte
>
> state = 0
>
> Do
> LockTask
> ' Toggle State if button is pressed.
> If (GetPin(InputPin) = ButtonPressed) Then
>
> State = State Xor 1 >
> ' Pause 0.1 s for button de-bounce.
> strMsg = "Button Pressed"
> call SendMessage(strMsg )
> Call Delay(1.0)
>
> ' Wait for release.
> Do Until (GetPin(InputPin) = ButtonReleased)
> state = state Xor 1
> Loop
> End If
> unlockTask
> call sleep(0.5)
>
> loop >
>
> end sub
>
> private sub SendMessage(strMsg as string)
> dim inCounter as integer
>
> strMsg = ">STX" & strMsg
> 'for incounter = 1 to 2
> Call PutQueueStr(Com3_Out, strMsg )
> debug.print strMsg
> 'next > End Sub
>
> Function MeasTemp() as Single
>
> Dim ADVal as Integer
> Dim Rtherm as Single, TK as Single, TC as Single, TF as Single >
>
> ADVal = GetADC(16) ' A/D conversion
> Rtherm = 10000.0/((1024.0/CSng(ADVal))-1.0) '
Calculate thermistor R
> TK = 1.0/(A_THERMISTOR + B_THERMISTOR *log(Rtherm)) '
T_Kelvin
> TC = TK-273.15 ' T_Celcius
> TF = (TC * 1.8) + 32.0 ' T_Fahr
> 'MeasTemp = TF
> MeasTemp = TC > End Function




Hummm...very very interesting.
Given the stated memory problem, I'd Sample by Exception.

Of the 300 samples, you are allocating RAM for each sample.
What if you only allocate only the changes, and a counter?
RAM USED then grows with each sample exception.
And an ADC would have to have a very unstable device attached, to give
enough exception sample readings to fill 300 RAM spaces with different
exception readings then the one just sample milliseconds before....to max
out expanding RAM USED space. Something even designed to pump values that
fast is more then likely too robust for a BX, anyway.

Soooo...Theoretically....were in the ball park for exception type RAM
storage.

Example:
ADC samples, say.... wave 1 thru 55 at the same value, then it changes.
RAM space 1 = Value of first 55 samples, and a counter with "55"
ADC samples 56 thru 105 at a different (exception) value.
RAM space 2 = Value of second samples, and a numeric counter.
ADC samples 106 thru 300, again, at a different (exception) value.
RAM space 3 = Value of the third samples, and a numeric counter.

Now you have 300 samples....but in less RAM space:
(Value 1 * Counter 1) + (Value 2 * Counter 2) + (Value 3 * Counter 3)
[RamSpace1] [RamSpace2] [RamSpace3]
One Ramspace = Length of Data Type for Value + Length of Data Type for
Counter

Now Im being overly liberal here in using only three exception waves but I
think you get the picture.
How many of the 300 samples in your example were of the same sample value?
How many were exceptions (values that changed)?

Like I said....very very interesting.

.db. -----Original Message-----
From: Frank Manning [mailto:]
Sent: Monday, June 23, 2003 2:52 PM
To:
Subject: Re: [BasicX] Can any one help From: Timber Wolfe <>

> From: Frank Manning:
> [...]
>> Also, by making variables static rather than local,
>> that memory is tied up permanently for the life of
>> the program. So that may actually make the problem
>> worse. [...]
>
> well if its the only thing the computer is doing (he
> gave us the code) does it matter if its permanant or
> not? [...]

Good question.

It might be easier to explain if we look at a simple example.

Suppose we need to find the standard deviation of 300 samples of 8
bit ADC data on one channel. Also suppose we need to do the same
thing for 150 samples of 10 bit ADC data on another channel.

Also assume that all data for one channel needs to be in memory at
the same time, but we need only one channel at a time. That is,
both channels don't need to be in memory simultaneously.

We can store the 8 bit data in 300 bytes. The 10 bit data also
requires 300 bytes, at 2 bytes per sample.

Right away we can see a problem -- we need at least 600 bytes of
storage, but the BX-24 has only 401 bytes of RAM.

An example program is shown below, where the samples are stored in
global variables as is fashionable on this forum. But the program
won't compile because it overflows RAM.

Is there another way of solving the problem, without increasing
RAM and without changing the algorithm for finding standard
deviation?

-- Frank Manning
-- NetMedia, Inc.

'------------------------
Option Explicit

Public Const LoResCount As Integer = 300
Public Const HiResCount As Integer = 150

Public LoRes(1 To LoResCount) As Byte
Public HiRes(1 To HiResCount) As Integer
'------------------------
Public Sub Main()

Dim L As Single
Dim H As Single

L = LoResStdDev

Debug.Print "LoRes standard deviation: "; CStr(L)

H = HiResStdDev

Debug.Print "HiRes standard deviation: "; CStr(H)

End Sub
'------------------------
Public Function LoResStdDev() As Single

' Returns the standard deviation of 300 samples of ADC data.
' The data consists of 8 bit samples from ADC pin 19. The
' sample rate is 512 samples per second.

Dim N As Integer
Dim Average As Single
Dim SumSquare As Single
Dim Residual As Single
Dim Variance As Single
Const Scale As Single = 255.0
Const Pin As Byte = 19

Average = 0.0
For N = 1 To LoResCount
Call DelayUntilClockTick
LoRes(N) = CByte(GetADC(Pin) \ 4) ' Reduce 2 bits.
Average = Average + (CSng(LoRes(N)) / Scale)
Next
Average = Average / CSng(LoResCount)

SumSquare = 0.0
For N = 1 To LoResCount
Residual = (CSng(LoRes(N)) / Scale) - Average
SumSquare = SumSquare + (Residual * Residual)
Next

Variance = SumSquare / CSng(LoResCount - 1)
LoResStdDev = Sqr(Variance)

End Function
'------------------------
Public Function HiResStdDev() As Single

' Returns the standard deviation of 150 samples of ADC data.
' The data consists of 10 bit samples from ADC pin 20. The
' sample rate is 512 samples per second.

Dim N As Integer
Dim Average As Single
Dim SumSquare As Single
Dim Residual As Single
Dim Variance As Single
Const Scale As Single = 1023.0
Const Pin As Byte = 19

Average = 0.0
For N = 1 To HiResCount
Call DelayUntilClockTick
HiRes(N) = GetADC(Pin)
Average = Average + (CSng(HiRes(N)) / Scale)
Next
Average = Average / CSng(HiResCount)

SumSquare = 0.0
For N = 1 To HiResCount
Residual = (CSng(HiRes(N)) / Scale) - Average
SumSquare = SumSquare + (Residual * Residual)
Next

Variance = SumSquare / CSng(HiResCount - 1)
HiResStdDev = Sqr(Variance)

End Function
'------------------------

Yahoo! Groups Sponsor

<http://rd.yahoo.com/M%1812.3170658.4537139.1261774/D=egroupweb/S065542
05:HM/A64415/R=0/SIGt6t7kdo/*http://www.netflix.com/Default?mqso`164
784&partid170658>

<http://us.adserver.yahoo.com/l?M%1812.3170658.4537139.1261774/D=egroupmai
l/S=:HM/A64415/rand0636223>

">http://docs.yahoo.com/info/terms/> .