Could you also post the SPIN code so that a comparison is possible?
As for conditional comparisons, they are possible, you just have to keep an eye on what you're doing (especially when the condition isn't met). Depending on what your SPIN code looks like it may be better to jump over the relevant code rather than rely on being able to cover it with more conditionals (this doesn't always work).
Re: order of values. Both get updated in rather large intervals. The comparison code can read the update between AN+0 and BN+0 or BN+0 and AN+1. In the first case it would read AN+0 and BN-1 in the second case AN+0 and BN+0.
There is a larger loop then this, as you could guess by all of the screen outputs, but this is what it looked like in the second screen capture where most of the pst updates were commented out so they didn't display. How do you suggest I control when the comparison code reads and outputs? Is there a best practice for this?
How do you suggest I control when the comparison code reads and outputs? Is there a best practice for this?
A few posts back you mentioned:
I need to tell the difference between channel 1's tooth 23 (I believe leading edge) and channel 2's tooth 3 underneath it, which will sometimes trail channel 1's tooth 23 and sometimes lead channel 1's tooth 23.
So for example you have event A and some time later event B which gives us a difference of C which is obtained say immediately after B occurred. We keep monitoring the time stamps and we get another A event next which has a difference of D (to the most recent :
----A----------------A-------
-----------------B-----------
| C | D |
Looking only at absolute differences, there is obviously a jump. This is repeated once we get the next B event. Can your math handle this? Also, provided you force B-more-recent-than-A as in your current code, your quote above (trail/lead) suggests that one tooth can overtake the other (correct me if I'm wrong). Which means that e.g. B may build up an increasing delta to (the previous) A, then it passes (the next) A which in turn introduces a jump toward smaller values again. Same issue (but less jumpy than with absolute measurements). Can you elaborate?
What I decided last night was to use tooth 26, instead of tooth 23. This allows me to not have situations where the difference is both positive and negative. Using tooth 26 and sans some sort of defect, A could never occur after B in a properly done measurement. Do you agree with this logic?
When you ask if my math can handle this, I think you are asking if I have code to alleviate this?If so, I have tried to do force B to be greater than A, as you know. The case you've pointed out where D was occurring was happening until I forced B to be greater than A and started using tooth 26. I did not consider that B could build a delta, but I believe the comparison code clears the values with the waitpeq mov command, if not that is a good point and maybe I'll throw in some code to ensure that the values are cleared when B is not greater than A, to make sure my code works as intended.
To reiterate, I've included an oscope measurement picture to make a little more sense of it. The pattern of channel 1 is: 34 peaks and valleys and then a "silence" for the length of 2 peaks/3valleys and the it repeats itself. The pattern for channel 2 is: peak1/valley1/peak2/valley2/peak3/longvalley(valley3) and then it repeats itself as shown in the scope picture. I am currently comparing the times of channel 2 peak3 which would be "A" to channel 1 peak26 which would be "B".
Peak3 will always happen before tooth 26 and never occur before tooth 21 or 22 (I have not been able to measure this yet to determine which one). Also, the time channel 2 takes to start over and repeat itself is 1/2 of the time channel 1 takes to repeat itself and start over.
I've discovered something interesting today ... my program is actually partially working, but seemingly slow to respond? Or something because it appears accurate at more constant values? I'm really not sure what is causing this yet, it obviously isn't PASM, so it has to be my code. It didn't show up when I had a steady state frequency, but it sure seems to be showing up when I use a varying frequency.
I am bench marking my results against a known good output, which has the frequency rate of about a 60hz shared serial channel (which ironically is the whole reason I did this project in the first place, because the response time of my benchmark is too slow, lol) of which it can output different values, one being the degree difference I am looking for.
I was able to drive around and screen capture the known good tool, my code outputted to the PST and the propscope. The propscope verifies that the known good benchmark tool is working and my code is not working. In the first picture they match, but I believe that is because the value was slow to change and was pretty steady. You'll see in the other pictures, they do not match at all.
I was thinking of building something that varied the frequency rate drastically over a few seconds, do you agree with this testing method to see what in my code is broken? I included the links to the pictures since they are entire screen captures, the forum will probably shrink them to where they are hard to read. I know in some of the propscope pictures I used cam tooth #1 instead of cam tooth #3, but the measurement is the same since it is exactly 180 out from cam tooth #3 and that frequency turns at 1/2 the speed of the channel above it. I can edit the pictures if it is too confusing.
To reiterate, I've included an oscope measurement picture to make a little more sense of it. The pattern of channel 1 is: 34 peaks and valleys and then a "silence" for the length of 2 peaks/3valleys and the it repeats itself. The pattern for channel 2 is: peak1/valley1/peak2/valley2/peak3/longvalley(valley3) and then it repeats itself as shown in the scope picture. I am currently comparing the times of channel 2 peak3 which would be "A" to channel 1 peak26 which would be "B".
OK, we are on the same page now. Thanks for clearing that up.
I was thinking of building something that varied the frequency rate drastically over a few seconds, do you agree with this testing method to see what in my code is broken?
That would certainly help (i.e. I pull here and it twitches over there). I'd cut down on the whole display code first. Just display the essential bits starting with input values and result, then go back from the result until the values match your expected values (or forward from the input). Also, using hex format may be less confusing than huge negative values (especially when timestamps are involved).
Not quite. I was more after something like the top right corner of your last screen. Both timestamps and their difference. That's just collection of data and one delta which it should be impossibe to mess up. Then somehow you arrive at comPst4 (which I assume is based on the timestamps). Provided the timestamps are correct something between those two points goes wrong.
IOW I was more concentrating on the history of the calculation(s). So anything which could vaguely duplicate real life data should be fine as input.
Also, you say it seems slow to respond. What is the behaviour when you go from constant value to another (e.g. 5sec A then switch to ? Does it kind of level out for the new value and if so how (immediately or smooth transition)?
What do you mean by the top right hand corner? That code block I pasted was the code I use to simulate the signal, when I was first writing the code and had not done anything with it real world. It generates the signal, but does not calculate it, and sends it from one pin on the prop to another through a resistor, and then receiving pin is the one that is monitored by the calculation code. I added the part to it last night that I've sectioned out and quoted in this post, to try and simulate the ranging that happens in the real world.
It works, it just is not responsive as shown by the pictures and therefore not accurate 1/2 of the time. I don't have any real world control (yet) of the values generated in the car, which is why I was trying to tweak the simulation code to create a range of values like what would happen in the car driving around.
Is that what you were asking?
if (autoRangeVVTI == true) and updateCnt < cnt ' autoRange set to true and updatecnt is less than cnt
updateCnt += autoRangeChangesPerSecond ' cycles based on how many times I want a degree added/subtracted per second
if advancing == true ' if advancing the cam
localCnt -= cyclesPerDegOfRot
degreesShifted += 1
if retarding == true ' if retarding the cam
localCnt += cyclesPerDegOfRot
degreesShifted -= 1
if degreesShifted =< 0 ' if 0, go back to advancing cam
advancing := true
retarding := false
if degreesShifted => 43 ' if 43, go back to retarding cam
advancing := false
retarding := true
I found one mistake, the bolded part used to be "if_nz".
This comparison calc problem is really giving me a hard time. I'm hoping this was the entire issue, but I'm not sure. I'm also having a hard time simulating the variable signal of the car. It seems to be accurate at a steady state frequency.
cmp lastCrGapTime, lastCaGapTime WZ, WC ' if crank time is greater
if_nz_and_c jmp #restart ' if not greater, go back to restart
cmp prevCaGapTime, lastCaGapTime WZ, WC ' make sure cam has rotated once to give a different value, before updating, lastCaGapTime should always be larger than prevCaGapTime
[b]if_nz_and_c[/b] wrlong lastCrGapTime, pstptr3
[b]if_nz_and_c[/b] sub lastCrGapTime, lastCaGapTime
[b]if_nz_and_c[/b] wrlong lastCaGapTime, pstptr2
[b]if_nz_and_c[/b] wrlong lastCrGapTime, pstptr
jmp #restart
It works, it just is not responsive as shown by the pictures and therefore not accurate 1/2 of the time. I don't have any real world control (yet) of the values generated in the car, which is why I was trying to tweak the simulation code to create a range of values like what would happen in the car driving around.
The last picture in post #36 shows a 21 in PST while the logging app(?) shows 36 instead. As both are circled I assume the should be the same. Is that correct? Then my question is, how do you arrive at 21 and where does the 36 come from? I mean you post all these code fragments but in the picture the 21 is only labelled as comPst4.
Ok, now I understand, sorry for the confusion, I should have explained that my apologies, if the pst pics are confusing just let me know. comPst4 = difference between the peak (center) of the square wave of the red channel (this channel is variable in reference to the other channel) and the center of the 26th tooth in the blue channel. Currently everything is in reference to tooth 26 on the channel that has far more teeth then the other one, the blue channel in this case.
My code is indicating there is a 21 degree difference, when in actuality it is a 36 degree difference as shown on the benchmark software and verified with the propscope. So pst/code shows 21, but in real life it is 36 degrees difference between the peak of the lower speed channel tooth and the peak of the higher speed channel's tooth 26.
I believe my code is slow to react and so I'm trying to figure out why that is. Please let me know if that doesn't make sense, I can write a long explanation in finite detail if you'd like me to.
The last picture in post #36 shows a 21 in PST while the logging app(?) shows 36 instead. As both are circled I assume the should be the same. Is that correct? Then my question is, how do you arrive at 21 and where does the 36 come from? I mean you post all these code fragments but in the picture the 21 is only labelled as comPst4.
Ok, looks like I need a total rewrite, my crank read object is catching about 20% of the amount of events it should in the actual environment and it catches 100% of them in the test environment. As much as I don't want to, my gut tells me I'd be better off starting over from scratch.
I finally got most of the bugs worked out and had some success tonight, what do you think of the PASM section of this code? Thank you very much for helping me get this far!
I had to create sort of a do --> until loop and I'm not sure if this was done in a way that is acceptable.
If this code is solid, I'm going to try and then use it to modify a solenoids pulse width. I guess I will have to build a target table and something that allows it to send different pulse widths based on how far it is from the target? I've never done anything like this before so I'm hoping to see some best practice examples to bench mark and save myself from having to learn the hard way how to do this properly.
You probably remember this, but crTAddr is the time stamp for crank TDC and caTAddr is the time stamp for camshaft TDC. They are compared and a calculation is done to figure out how many degrees caTAddr is ahead of crTAddr. Also, how do you divide by 10 in PASM?
var
long cog
long crTAddr
long caTAddr
long pst
long pst2
long pst3
long pst4
long pst5
long pst6
long pst7
long pst8
long pst9
long pst10
long pst11
long pst12
long pst13
long pst14
long pst15
long pst16
PUB selftest | r, a
init(@r, @a)
r := 0
a := 0
dira[16..23]~~
repeat
r?
?a
waitcnt(clkfreq + cnt)
outa[16..23] := getPst
pub init(cr, ca)
waitcnt((clkfreq*2) + cnt) ' let screen initialize
crTAddr := cr
caTAddr := ca
return cog := cognew(@diffcntr, @crTAddr) + 1
pub cleanup
'' Stop frequency counter cog if running
if cog
cogstop(cog~ - 1)
pub getCrTAddr
result := crTAddr
pub getCaTAddr
result := caTAddr
pub getPst
result := pst
pub getPst2
result := pst2
pub getPst3
result := pst3
pub getPst4
result := pst4
pub getPst5
result := pst5
pub getPst6
result := pst6
pub getPst7
result := pst7
pub getPst8
result := pst8
pub getPst9
result := pst9
pub getPst10
result := pst10
pub getPst11
result := pst11
pub getPst12
result := pst12
pub getPst13
result := pst13
pub getPst14
result := pst14
pub getPst15
result := pst15
pub getPst16
result := pst16
DAT org 0
diffcntr add crtptr, par ' @crTAddr
add catptr, par ' @caTAddr
add pstptr, par ' @pst
add pstptr2, par ' @pst2
add pstptr3, par ' @pst3
add pstptr4, par ' @pst4
add pstptr5, par ' @pst5
add pstptr6, par ' @pst6
add pstptr7, par ' @pst7
add pstptr8, par ' @pst8
add pstptr9, par ' @pst9
add pstptr10, par ' @pst10
add pstptr11, par ' @pst11
add pstptr12, par ' @pst12
add pstptr13, par ' @pst13
add pstptr14, par ' @pst14
add pstptr15, par ' @pst15
add pstptr16, par ' @pst16
rdlong crtptr, crtptr ' cr
rdlong catptr, catptr ' ca
jmp #restart
waitforcrvalue
'mov prevCrGapTime, lastCrGapTime
rdlong lastCrGapTime, crtptr ' read long[cr]
cmp lastCrGapTime, lastCaGapTime WZ, WC ' compare crank to cam
if_nz_and_c jmp #waitforcrvalue ' if crank is less than cam, jump to waitforcrvalue
if_nc wrlong lastCrGapTime, pstptr13
if_nc jmp #continue
restart
mov prevCaGapTime, lastCaGapTime
rdlong lastCaGapTime, catptr ' long[ca]
cmp prevCaGapTime, lastCaGapTime WZ, WC ' compare current cam gap time to previous cam gap time
if_z_and_nc jmp #restart
if_nz_and_nc jmp #restart ' if equal, go to restart
if_nz_and_c wrlong lastCaGapTime, pstptr14
if_nz_and_c jmp #waitforcrvalue
continue
wrlong lastCrGapTime, pstptr2 ' write crank to pst
mov lastCrGapTimeT, lastCrGapTime ' move crank to crank temp
wrlong lastCaGapTime, pstptr3 ' write cam to pst
sub lastCrGapTimeT, lastCaGapTime ' subtract cam from crank temp
wrlong lastCrGapTimeT, pstptr ' write gaptime to pst
jmp #restart
' --------------------------------------------------------------------------------------------------
crtptr long 0
catptr long 4
pstptr long 8
pstptr2 long 12
pstptr3 long 16
pstptr4 long 20
pstptr5 long 24
pstptr6 long 28
pstptr7 long 32
pstptr8 long 36
pstptr9 long 40
pstptr10 long 44
pstptr11 long 48
pstptr12 long 52
pstptr13 long 56
pstptr14 long 60
pstptr15 long 64
pstptr16 long 68
' Standard variable initialization here
lastCrGapTime long 0
lastCrGapTimeT long 0
lastCaGapTime long 0
prevCrGapTime long 0
prevCaGapTime long 0
' Reserved variables here
tmp1 res 1
tmp2 res 1
fit
The logic could be written a bit simpler. No point jumping all over the place only to come back a few clocks later. I keep mixing up crank and cam, which one is the 26th-tooth-signal? I assume crank ATM. So given that you finally calculate crank - cam shouldn't you be waiting for a change in crank and then simply sample cam? Otherwise you may end up with sampling peak 2 (post #35) rather than 1 or 3. Correct me if I'm wrong.
restart mov prevCaGapTime, lastCaGapTime
waitforcavalue rdlong lastCaGapTime, catptr ' long[ca]
cmp prevCaGapTime, lastCaGapTime WZ, WC ' compare current to previous cam gap time
if_ae jmp #waitforcavalue
wrlong lastCaGapTime, pstptr14
waitforcrvalue rdlong lastCrGapTime, crtptr ' long[cr]
cmp lastCrGapTime, lastCaGapTime WZ, WC ' compare crank to cam
if_b jmp #waitforcrvalue ' if crank is less than cam, jump to waitforcrvalue
wrlong lastCrGapTime, pstptr13
wrlong lastCrGapTime, pstptr2 ' write crank to pst
mov lastCrGapTimeT, lastCrGapTime ' move crank to crank temp
wrlong lastCaGapTime, pstptr3 ' write cam to pst
sub lastCrGapTimeT, lastCaGapTime ' subtract cam from crank temp
wrlong lastCrGapTimeT, pstptr ' write gaptime to pst
jmp #restart
Also, given the number of addresses you resolve in the init phase it may be beneficial to do that in a loop later. It doesn't do any harm right now though.
As for division by 10, unless you can map that to powers of 2 it's going to be the hard way, e.g. Propeller Manual Appendix B and friends.
The reason I have to wait for cam first is because the cam (3 tooth wheel) is 1/2 the frequency rate of the crank (34 tooth wheel).
I have my cam calculation write a cnt value when tooth 3 of the cam wheel passes
I have my crank calculation write a cnt value when tooth 26 of the crank wheel passes (which passes twice for each time the cam passes tooth 3 and only 1 of those crank passes is valid)
The cam is exactly 1/2 the revolution frequency rate of the crank if you were measuring the time from a single tooth to that same tooth the next time around. This is the reason I wait for cam, because I need to compare cam tooth3 to crank tooth 26 when they are very close, not when cam tooth3 is 180 out on the preceding or following time tooth 26 comes around.
I know this is kind of confusing, and I may not have done a great job explaining it, so I made a diagram even though you probably don't need it to understand. It's pretty terrible as far as artistry, but I think it does well as far as function and might make it easier to picture in your head.
The logic could be written a bit simpler. No point jumping all over the place only to come back a few clocks later. I keep mixing up crank and cam, which one is the 26th-tooth-signal? I assume crank ATM. So given that you finally calculate crank - cam shouldn't you be waiting for a change in crank and then simply sample cam? Otherwise you may end up with sampling peak 2 (post #35) rather than 1 or 3. Correct me if I'm wrong.
The reason I have to wait for cam first is because the cam (3 tooth wheel) is 1/2 the frequency rate of the crank (34 tooth wheel).
I have my cam calculation write a cnt value when tooth 3 of the cam wheel passes. I have my crank calculation write a cnt value when tooth 26 of the crank wheel passes (which passes twice for each time the cam passes tooth 3 and only 1 of those crank passes is valid).
OK, that explains it. Thanks. I was under the impression that each cam tooth (1/2/3) is recorded with timestamp. If it's only ever tooth 3 then the logic is fine.
As an update to this (in case it comes up in a search), I keep getting roll over runaway / lockup, so I had to add the following code to make sure when I compare the two numbers, that I was comparing to positive numbers to two positive numbers and subtracting, or two negative numbers to two negative numbers and subtracting.
I don't know if this is the best way to do it, but it worked after I implemented it and I didn't find a better way when searching through old posts.
I'm also doing PASM division (thank you Kye) with the second code block, instead of wasting time inside of my com loop with spin division, that way the com loop just spits out data and loops as fast as it can.
cmps lastCrGapTime, zero WZ, WC ' compare SIGNED to see if number is greater or less than 0
if_nc mov crState, #1 ' greater or equal to 0
if_nz_and_c mov crState, #0 ' less than 0
wrlong crState, pstptr10
cmps lastCaGapTime, zero WZ, WC ' compare SIGNED to see if number is greater or less than 0
if_nc mov caState, #1 ' greater or equal to 0
if_nz_and_c mov caState, #0 ' less than 0
wrlong caState, pstptr11
cmp crState, caState WZ, WC ' make sure both numbers are greater or less than 0 together
if_nz jmp #restart ' if not equal, bail out and start over
As an update to this (in case it comes up in a search), I keep getting roll over runaway / lockup, so I had to add the following code to make sure when I compare the two numbers, that I was comparing to positive numbers to two positive numbers and subtracting, or two negative numbers to two negative numbers and subtracting.
I don't quite see how un/signedness is important with the times involved here. Do you have an example?
Here is what I have from the last time this happened, crank has to always be later then cam, so a smaller negative number or larger positive number, depending on where in the clk cycle we are at and upon rollover it would go positive and not be treated as "later"? And the only way it would unfreeze would be if crank time happened to randomly hit a value between -1 and -162603? It would lock up within 5 minutes of use on both the negative rollover and positive roll over, but I ran it for 3 hours today after this and it did not lock up. What do you think?
Maybe the project would help? Pardon the messy messy code and lots of commented out things.
To duplicate this you could flash a prop with this code, I believe the only additional things needed would be pin 2 feeding pin 3 via a 100ohm resistor and pin 4 feeding pin 5 via a 100ohm resistor.
I just tested this code and it endlessly looped the first time it rolled over from negative to positive.
A (timestamp) difference between cnt values is good for up to 26sec (@80MHz).
With the above values you get -115734 ($FFFE3BEA) and -162604 ($FFFD84D4), so crank time (the former) is later than cam time (the latter). To avoid the rollover issue you could simply always calculate the delta and do the comparison on the delta. So the first loop can simply check for not equal meaning timestamp has changed, and the second loop reads the timestamp, calculates the delta and goes from there.
comPst2 (crank) and comPst3 (cam) are constantly comparing cnts (with comPst2 being "later") and comPst2-comPst3 is printed at comPst. A calc is then done against comPst to output a difference converted to degrees at comPst4.
Does that make sense? I'm working on putting labeled information at the top of the screen as we speak so that it's easier to interpret, but it isn't done yet
Thank you. I'm going to compare tomorrow at work where I have a few monitors and try and figure out how my code was shrunk so dramatically so I can learn.
Comments
As for conditional comparisons, they are possible, you just have to keep an eye on what you're doing (especially when the condition isn't met). Depending on what your SPIN code looks like it may be better to jump over the relevant code rather than rely on being able to cover it with more conditionals (this doesn't always work).
Re: order of values. Both get updated in rather large intervals. The comparison code can read the update between AN+0 and BN+0 or BN+0 and AN+1. In the first case it would read AN+0 and BN-1 in the second case AN+0 and BN+0.
There is a larger loop then this, as you could guess by all of the screen outputs, but this is what it looked like in the second screen capture where most of the pst updates were commented out so they didn't display. How do you suggest I control when the comparison code reads and outputs? Is there a best practice for this?
A few posts back you mentioned:
So for example you have event A and some time later event B which gives us a difference of C which is obtained say immediately after B occurred. We keep monitoring the time stamps and we get another A event next which has a difference of D (to the most recent : Looking only at absolute differences, there is obviously a jump. This is repeated once we get the next B event. Can your math handle this? Also, provided you force B-more-recent-than-A as in your current code, your quote above (trail/lead) suggests that one tooth can overtake the other (correct me if I'm wrong). Which means that e.g. B may build up an increasing delta to (the previous) A, then it passes (the next) A which in turn introduces a jump toward smaller values again. Same issue (but less jumpy than with absolute measurements). Can you elaborate?
What I decided last night was to use tooth 26, instead of tooth 23. This allows me to not have situations where the difference is both positive and negative. Using tooth 26 and sans some sort of defect, A could never occur after B in a properly done measurement. Do you agree with this logic?
When you ask if my math can handle this, I think you are asking if I have code to alleviate this?If so, I have tried to do force B to be greater than A, as you know. The case you've pointed out where D was occurring was happening until I forced B to be greater than A and started using tooth 26. I did not consider that B could build a delta, but I believe the comparison code clears the values with the waitpeq mov command, if not that is a good point and maybe I'll throw in some code to ensure that the values are cleared when B is not greater than A, to make sure my code works as intended.
To reiterate, I've included an oscope measurement picture to make a little more sense of it. The pattern of channel 1 is: 34 peaks and valleys and then a "silence" for the length of 2 peaks/3valleys and the it repeats itself. The pattern for channel 2 is: peak1/valley1/peak2/valley2/peak3/longvalley(valley3) and then it repeats itself as shown in the scope picture. I am currently comparing the times of channel 2 peak3 which would be "A" to channel 1 peak26 which would be "B".
Peak3 will always happen before tooth 26 and never occur before tooth 21 or 22 (I have not been able to measure this yet to determine which one). Also, the time channel 2 takes to start over and repeat itself is 1/2 of the time channel 1 takes to repeat itself and start over.
----A
A
B
| C | D |
I am bench marking my results against a known good output, which has the frequency rate of about a 60hz shared serial channel (which ironically is the whole reason I did this project in the first place, because the response time of my benchmark is too slow, lol) of which it can output different values, one being the degree difference I am looking for.
I was able to drive around and screen capture the known good tool, my code outputted to the PST and the propscope. The propscope verifies that the known good benchmark tool is working and my code is not working. In the first picture they match, but I believe that is because the value was slow to change and was pretty steady. You'll see in the other pictures, they do not match at all.
I was thinking of building something that varied the frequency rate drastically over a few seconds, do you agree with this testing method to see what in my code is broken? I included the links to the pictures since they are entire screen captures, the forum will probably shrink them to where they are hard to read. I know in some of the propscope pictures I used cam tooth #1 instead of cam tooth #3, but the measurement is the same since it is exactly 180 out from cam tooth #3 and that frequency turns at 1/2 the speed of the channel above it. I can edit the pictures if it is too confusing.
http://img19.imageshack.us/img19/7318/slightlyoffdegrees8.jpg
http://img195.imageshack.us/img195/1242/slightlyoffdegrees9.jpg
http://img17.imageshack.us/img17/9475/slightlyoffdegrees10.jpg
http://img528.imageshack.us/img528/8148/slightlyoffdegrees11.jpg
IOW I was more concentrating on the history of the calculation(s). So anything which could vaguely duplicate real life data should be fine as input.
Also, you say it seems slow to respond. What is the behaviour when you go from constant value to another (e.g. 5sec A then switch to ? Does it kind of level out for the new value and if so how (immediately or smooth transition)?
What do you mean by the top right hand corner? That code block I pasted was the code I use to simulate the signal, when I was first writing the code and had not done anything with it real world. It generates the signal, but does not calculate it, and sends it from one pin on the prop to another through a resistor, and then receiving pin is the one that is monitored by the calculation code. I added the part to it last night that I've sectioned out and quoted in this post, to try and simulate the ranging that happens in the real world.
It works, it just is not responsive as shown by the pictures and therefore not accurate 1/2 of the time. I don't have any real world control (yet) of the values generated in the car, which is why I was trying to tweak the simulation code to create a range of values like what would happen in the car driving around.
Is that what you were asking?
This comparison calc problem is really giving me a hard time. I'm hoping this was the entire issue, but I'm not sure. I'm also having a hard time simulating the variable signal of the car. It seems to be accurate at a steady state frequency.
Ok, now I understand, sorry for the confusion, I should have explained that my apologies, if the pst pics are confusing just let me know. comPst4 = difference between the peak (center) of the square wave of the red channel (this channel is variable in reference to the other channel) and the center of the 26th tooth in the blue channel. Currently everything is in reference to tooth 26 on the channel that has far more teeth then the other one, the blue channel in this case.
My code is indicating there is a 21 degree difference, when in actuality it is a 36 degree difference as shown on the benchmark software and verified with the propscope. So pst/code shows 21, but in real life it is 36 degrees difference between the peak of the lower speed channel tooth and the peak of the higher speed channel's tooth 26.
I believe my code is slow to react and so I'm trying to figure out why that is. Please let me know if that doesn't make sense, I can write a long explanation in finite detail if you'd like me to.
http://img27.imageshack.us/img27/6536/slightlyoffdegrees11b.jpg
I finally got most of the bugs worked out and had some success tonight, what do you think of the PASM section of this code? Thank you very much for helping me get this far!
I had to create sort of a do --> until loop and I'm not sure if this was done in a way that is acceptable.
If this code is solid, I'm going to try and then use it to modify a solenoids pulse width. I guess I will have to build a target table and something that allows it to send different pulse widths based on how far it is from the target? I've never done anything like this before so I'm hoping to see some best practice examples to bench mark and save myself from having to learn the hard way how to do this properly.
You probably remember this, but crTAddr is the time stamp for crank TDC and caTAddr is the time stamp for camshaft TDC. They are compared and a calculation is done to figure out how many degrees caTAddr is ahead of crTAddr. Also, how do you divide by 10 in PASM?
As for division by 10, unless you can map that to powers of 2 it's going to be the hard way, e.g. Propeller Manual Appendix B and friends.
I have my cam calculation write a cnt value when tooth 3 of the cam wheel passes
I have my crank calculation write a cnt value when tooth 26 of the crank wheel passes (which passes twice for each time the cam passes tooth 3 and only 1 of those crank passes is valid)
The cam is exactly 1/2 the revolution frequency rate of the crank if you were measuring the time from a single tooth to that same tooth the next time around. This is the reason I wait for cam, because I need to compare cam tooth3 to crank tooth 26 when they are very close, not when cam tooth3 is 180 out on the preceding or following time tooth 26 comes around.
I know this is kind of confusing, and I may not have done a great job explaining it, so I made a diagram even though you probably don't need it to understand. It's pretty terrible as far as artistry, but I think it does well as far as function and might make it easier to picture in your head.
Does that help explain it?
I don't know if this is the best way to do it, but it worked after I implemented it and I didn't find a better way when searching through old posts.
I'm also doing PASM division (thank you Kye) with the second code block, instead of wasting time inside of my com loop with spin division, that way the com loop just spits out data and loops as fast as it can.
Crank time: -115734
Cam time: -162604
To duplicate this you could flash a prop with this code, I believe the only additional things needed would be pin 2 feeding pin 3 via a 100ohm resistor and pin 4 feeding pin 5 via a 100ohm resistor.
I just tested this code and it endlessly looped the first time it rolled over from negative to positive.
A (timestamp) difference between cnt values is good for up to 26sec (@80MHz).
With the above values you get -115734 ($FFFE3BEA) and -162604 ($FFFD84D4), so crank time (the former) is later than cam time (the latter). To avoid the rollover issue you could simply always calculate the delta and do the comparison on the delta. So the first loop can simply check for not equal meaning timestamp has changed, and the second loop reads the timestamp, calculates the delta and goes from there.
Does that make sense? I'm working on putting labeled information at the top of the screen as we speak so that it's easier to interpret, but it isn't done yet