1. I was wondering about .01*100. That didn't make sense.

2. yeah, just noticed a bracket error too, made an edit to my post.

For those following along...
BOTH METHODS WORK
Pick a method and go with it.

3. Originally Posted by hjtrbo
Your formula is wrong. You're incorrectly normalising your fuel trims and there is an erroneous bracket.

([50040.71]*(1+((.01*[50116]*100)+(.01*[50114]*100)))-(([50030.92]*[2312]/[2126.240])*[50070.56]/60*4))/(([50030.92]*[2312]/[2126.240])*[50070.56]/60*4))*100

Here is a 3% discrepancy between your implementation of smokes formula, which would account for the error you are seeing between the 2 methods.
Attachment 135829

Try this
([50040.71]*(1+(.01*[50116.156]+.01*[50114.156]))-(([50030.92]*[2312]/[2126.240])*[50070.56]/60*4))/(([50030.92]*[2312]/[2126.240])*[50070.56]/60*4)*100

Considerations:
Try average function

WOW THANK YOU! That made a world of difference! I don't know why smoke didn't ever provide this feedback the 162 times I asked for help before. I received that formula when I was experiencing issues and another member PM'd me that one. I will delete all other GMVE formulas I have and use this one instead.

I am going to continue looking at the logs and comparing. Right off the hop (looking at the chart view averages) both methods seems to more or less agree with each other. However, it appears using Dynamic Air is superior because...

As I noted before (over the last year+) GMVE seems to amplify the differences in error. Meaning maybe the dynamic air method shows -2%, GMVE will show -4% and so on.
Also at idle, GMVE is all over the place!
I think both of these can be attributed to the fact that Dynamic Air is filtered to calm the excessive static sensor noise...which is another reason why I feel this is the better option.

Here is what I see at idle...one thing to note is that I had to change my view from +/-10% to +/-20% to fit the data, and even then GMVE is still swinging off the charts.
idle.jpg

And when we look at the idle area on the 3D graph, you can GMVE makes the red A LOT more red and the green A LOT more green
chart.jpg

And if we plot on a real histogram we can see again a tighter data grouping using dynamic air and more defined bell curve (-6/+15 compared to -11/+16)
histo.jpg

As far as polling interval...I have a secret weapon! LOL
fast poll.jpg

4. Yes, GMVE does bounce around. I filter mine with .average(200). Makes the formula real ugly.

5. Not sure if you ever seen my GMVE formula builder spreadsheet.

6. Originally Posted by hjtrbo
Not sure if you ever seen my GMVE formula builder spreadsheet.

Been using that since Nov 2021 when I found out about it!

7. Nathan, maybe you and Daniel should work together and make an even better VVE tool? Hmmmm...

See good things come from discussion and working together

8. One step ahead of you Greg. Not sure if he's seen my private message yet. Just been having a play with numpy. I think that will get the coefficients generated.

9. Knew you could figure it out...

10. Can confirm numpy and scipy in a python script will do it. Grabbed zone 6 of my VE table, added some random percentage, copied the new values to my script, hit run and also hit calc coefficients on the VE editor. They both generate the same coefficients!!! HP must be using the same algo to curve fit. My first crack at python... And help from chatGPT

Screenshot 2023-08-19 160154.png

Here is the test code for zone 6:
Code:
```import numpy as np
from scipy.optimize import curve_fit

# Given data
MAP = [10, 15, 20, 25, 30, 35, 40, 45]
RPM = [1000, 1250, 1500, 1750]
measurement = [
[717.6177678,   822.4499492,    921.87393,      1015.88971],
[838.2188358,   974.5,          1071.25,        1116.065835],
[943.6033685,   1138.300813,    1232.688901,    1201.025425],
[1033.771366,   1229.996465,    1316.895406,    1270.768479],
[1108.722828,   1304.953927,    1384.363723,    1325.294998],
[1168.457755,   1363.173201,    1435.093851,    1364.604982],
[1212.976146,   1324.5,         1385.5,         1388.69843],
[1242.278002,   1299.451983,    1351.217763,    1397.575343],
]

# Define the model function
def model_func(data, constant, coefficient_a, coefficient_b, coefficient_c, coefficient_d, coefficient_e):
MAP, RPM = data
return constant + coefficient_a * MAP + coefficient_b * MAP**2 + coefficient_c * MAP * RPM + coefficient_d * RPM + coefficient_e * RPM**2

# Reshape data for curve fitting
X = np.array(np.meshgrid(MAP, RPM)).T.reshape(-1, 2).T
Y = np.array(measurement).flatten()

# Perform curve fitting
initial_guess = [1, 1, 1, 1, 1, 1]  # Initial guess for coefficients
params, _ = curve_fit(model_func, X, Y, p0=initial_guess)

constant, coefficient_a, coefficient_b, coefficient_c, coefficient_d, coefficient_e = params
print("Constant:", constant)
print("Coefficient[a]:", coefficient_a)
print("Coefficient[b]:", coefficient_b)
print("Coefficient[c]:", coefficient_c)
print("Coefficient[d]:", coefficient_d)
print("Coefficient[e]:", coefficient_e)```

11. Originally Posted by hjtrbo
Can confirm numpy and scripy in a python script will do it. Grabbed zone 6 of my VE table, added some random percentage, copied the new values to my script, hit run and also hit calc coefficients on the VE editor. They both generate the same coefficients!!! HP must be using the same algo to curve fit. Not bad for my first crack at python lol.

Screenshot 2023-08-19 160154.png

Here is the test code for zone 6:
Code:
```import numpy as np from scipy.optimize import curve_fit

# Given data
MAP = [10, 15, 20, 25, 30, 35, 40, 45]
RPM = [1000, 1250, 1500, 1750]
measurement = [
[717.6177678,   822.4499492,    921.87393,      1015.88971],
[838.2188358,   974.5,          1071.25,        1116.065835],
[943.6033685,   1138.300813,    1232.688901,    1201.025425],
[1033.771366,   1229.996465,    1316.895406,    1270.768479],
[1108.722828,   1304.953927,    1384.363723,    1325.294998],
[1168.457755,   1363.173201,    1435.093851,    1364.604982],
[1212.976146,   1324.5,         1385.5,         1388.69843],
[1242.278002,   1299.451983,    1351.217763,    1397.575343],
]

# Define the model function
def model_func(data, constant, coefficient_a, coefficient_b, coefficient_c, coefficient_d, coefficient_e):
MAP, RPM = data
return constant + coefficient_a * MAP + coefficient_b * MAP**2 + coefficient_c * MAP * RPM + coefficient_d * RPM + coefficient_e * RPM**2

# Reshape data for curve fitting
X = np.array(np.meshgrid(MAP, RPM)).T.reshape(-1, 2).T
Y = np.array(measurement).flatten()

# Perform curve fitting
initial_guess = [1, 1, 1, 1, 1, 1]  # Initial guess for coefficients
params, _ = curve_fit(model_func, X, Y, p0=initial_guess)

constant, coefficient_a, coefficient_b, coefficient_c, coefficient_d, coefficient_e = params
print("Constant:", constant)
print("Coefficient[a]:", coefficient_a)
print("Coefficient[b]:", coefficient_b)
print("Coefficient[c]:", coefficient_c)
print("Coefficient[d]:", coefficient_d)

print("Coefficient[e]:", coefficient_e)```
Wow really nice work!
plotted.png

12. Originally Posted by hjtrbo
Can confirm numpy and scripy in a python script will do it. Grabbed zone 6 of my VE table, added some random percentage, copied the new values to my script, hit run and also hit calc coefficients on the VE editor. They both generate the same coefficients!!! HP must be using the same algo to curve fit. Not bad for my first crack at python lol. And help from chatGPT

Screenshot 2023-08-19 160154.png

Here is the test code for zone 6:
Code:
```import numpy as np
from scipy.optimize import curve_fit

# Given data
MAP = [10, 15, 20, 25, 30, 35, 40, 45]
RPM = [1000, 1250, 1500, 1750]
measurement = [
[717.6177678,   822.4499492,    921.87393,      1015.88971],
[838.2188358,   974.5,          1071.25,        1116.065835],
[943.6033685,   1138.300813,    1232.688901,    1201.025425],
[1033.771366,   1229.996465,    1316.895406,    1270.768479],
[1108.722828,   1304.953927,    1384.363723,    1325.294998],
[1168.457755,   1363.173201,    1435.093851,    1364.604982],
[1212.976146,   1324.5,         1385.5,         1388.69843],
[1242.278002,   1299.451983,    1351.217763,    1397.575343],
]

# Define the model function
def model_func(data, constant, coefficient_a, coefficient_b, coefficient_c, coefficient_d, coefficient_e):
MAP, RPM = data
return constant + coefficient_a * MAP + coefficient_b * MAP**2 + coefficient_c * MAP * RPM + coefficient_d * RPM + coefficient_e * RPM**2

# Reshape data for curve fitting
X = np.array(np.meshgrid(MAP, RPM)).T.reshape(-1, 2).T
Y = np.array(measurement).flatten()

# Perform curve fitting
initial_guess = [1, 1, 1, 1, 1, 1]  # Initial guess for coefficients
params, _ = curve_fit(model_func, X, Y, p0=initial_guess)

constant, coefficient_a, coefficient_b, coefficient_c, coefficient_d, coefficient_e = params
print("Constant:", constant)
print("Coefficient[a]:", coefficient_a)
print("Coefficient[b]:", coefficient_b)
print("Coefficient[c]:", coefficient_c)
print("Coefficient[d]:", coefficient_d)
print("Coefficient[e]:", coefficient_e)```
If you move the 3d graph will it spit the new coefficients out? I see good things coming

13. Dynamic Airflow calculation method used in Gen4 and Gen5 is described in this patent:

But it's still partial. Patent only describes Current and Next airmass, but controller calculates further Next2 airmass. And there is a lot of safety limits applied to predicted airmass.

Originally Posted by hjtrbo
Lots of things we can't see. 14,721 tables in this particular E38 calibration.

Attachment 135756
Hmmm... How did you put your hands on this treasure?

14. Originally Posted by hjtrbo
Not sure if you ever seen my GMVE formula builder spreadsheet.

Thank you for this. I remember filling out this spreadsheet a couple years ago...I thought that is where I got my original formula from...maybe I got an older version that had some bugs, or I had some copy and paste issues. Anyway...long story longer...I filled out just and use the suggested in 200ms average and that definitely calmed down the peaks. Again, a million thanks!

15. Originally Posted by verlon
Hmmm... How did you put your hands on this treasure?
Up for swaps if you have E67 or T43

16. I think he means how was all that data obtained? I'm interested, too.

17. I had some thoughts about all this concerning points of logic. What's a better tune SD, MAF, or hybrid? It's along the lines of when tuning CL use the narrowbands to tune. Tuning the system in the same configuration as final running conditions yields the most accurate results. In SD tune VE, MAF do MAF, but hybrid do SD and MAF separately? I'm coming around 180 on this hybrid tuning idea. It does make more sense. Tune MAF/VE hybrid in hybrid mode. We're tuning the entire system.

So Cringer I have to give you credit you're really onto something, and I apologize for my skepticism. You correctly determined that to understand this particular GM MAF/MAP hybrid control scheme one needs to pay attention to Dynamic Airflow. The patent that verlon posted reinforces the Dynamic Airflow method.

Still, I have problems with the implementation. How to determine steady state and how to determine how much each airflow model is corrected?

1) For the first part of determining steady state conditions I haven't seen any quantifiable yes/no. Seems more like qualification, a 'feel' thing, which has no place in an accurate model. That was until verlon provided a patent document that contains a wealth of information. It shows how steady state is determined.

What I propose is a modification to the dynair filter. This will allow more accurate determination of what the control scheme considers steady state, therefore will provide more accurate results.

This is very much pseudocode. Maybe someone who's more competent with VCM Scanner can translate it to math filter format. Whether or not this matches what's being described in the patent needs verification:

Code:
`Poll [DynAir] if {abs([MAF(k)]-[MAF(k-1)])/[MAF(k-1)] <= [ECM 13432]} && {abs([MAP(k)]-[MAP(k-1)])/[MAP(k-1)] <= [ECM 13432]}`
- where k = current time, k-1 = current time - polling rate. So MAF(k) = MAF reading now and MAF(k-1) = MAF reading .250 seconds ago, for example.
- ECM 13432 = Dynamic Airflow Current Gain (0.1)

All it's saying is things are steady state while both MAF and MAP have each changed 10% or less. Assumptions are made about k-1 timestep being the polling rate and gain being ECM 13432.

Here's my scribbles on how I came up with it.
quick notes.png

Hope this helps.

18. Originally Posted by SiriusC1024
I had some thoughts about all this concerning points of logic. What's a better tune SD, MAF, or hybrid? It's along the lines of when tuning CL use the narrowbands to tune. Tuning the system in the same configuration as final running conditions yields the most accurate results. In SD tune VE, MAF do MAF, but hybrid do SD and MAF separately? I'm coming around 180 on this hybrid tuning idea. It does make more sense. Tune MAF/VE hybrid in hybrid mode. We're tuning the entire system.

So Cringer I have to give you credit you're really onto something, and I apologize for my skepticism. You correctly determined that to understand this particular GM MAF/MAP hybrid control scheme one needs to pay attention to Dynamic Airflow. The patent that verlon posted reinforces the Dynamic Airflow method.

Still, I have problems with the implementation. How to determine steady state and how to determine how much each airflow model is corrected?

1) For the first part of determining steady state conditions I haven't seen any quantifiable yes/no. Seems more like qualification, a 'feel' thing, which has no place in an accurate model. That was until verlon provided a patent document that contains a wealth of information. It shows how steady state is determined.

What I propose is a modification to the dynair filter. This will allow more accurate determination of what the control scheme considers steady state, therefore will provide more accurate results.

This is very much pseudocode. Maybe someone who's more competent with VCM Scanner can translate it to math filter format. Whether or not this matches what's being described in the patent needs verification:

Code:
`Poll [DynAir] if {abs([MAF(k)]-[MAF(k-1)])/[MAF(k-1)] <= [ECM 13432]} && {abs([MAP(k)]-[MAP(k-1)])/[MAP(k-1)] <= [ECM 13432]}`
- where k = current time, k-1 = current time - polling rate. So MAF(k) = MAF reading now and MAF(k-1) = MAF reading .250 seconds ago, for example.
- ECM 13432 = Dynamic Airflow Current Gain (0.1)

All it's saying is things are steady state when both MAF and MAP have each changed 10% or less. Assumptions are made about k-1 timestep being the polling rate and gain being ECM 13432.

Here's my scribbles on how I came up with it.
quick notes.png

Hope this helps.
Wouldn't it be better to set it up with less than 10%? In other words something like 5% or less or would that be too aggressive at least for the MAF - probably right for the map? I only ask because I know transients come into play when the rpm's are changing 50 or more. I found this out years ago playing with transient settings on a big cammed motor where I had it "thumping" pretty good and before I realized it I was idling at a 13.9 afr because transients had kicked in as I had them set pretty aggressive as it was a big blower motor. Or just use the time function and let things be?

19. If I am correct about the assignment of the gain constant being ECM 13432 then all you'd have to do is change those from 0.1 to 0.05 to make it 5%. So that would be a tuning technique to employ with larger cams and running MAF/MAP hybrid if necessary.

But, again assumming ECM 13432, one could theoretically alter the allowance between MAP and MAF for various engine loads. Tighten it up for idle but allow more at other ranges. Just have to modify the filter to account for differences in that table.

You're probably right though. A higher polling rate/smaller time interval should clear things up. Actually, what the smaller time interval is doing is allowing a smaller window for mismatch between MAF and MAP. With transients there's lag between the two sensors. So, I think the formula should be valid in all conditions. Wouldn't even need a TPS or RPM filter.

Question is what is the actual polling rate of the ECU. How often is the control loop updated? That would be the determining factor.

Try it out and see how it goes.

p.s. Can someone post up a .csv log with map, maf, vve, dynair tracked? I want to demonstrate the filter graphically.

20. Originally Posted by SiriusC1024
I had some thoughts about all this concerning points of logic. What's a better tune SD, MAF, or hybrid? It's along the lines of when tuning CL use the narrowbands to tune. Tuning the system in the same configuration as final running conditions yields the most accurate results. In SD tune VE, MAF do MAF, but hybrid do SD and MAF separately? I'm coming around 180 on this hybrid tuning idea. It does make more sense. Tune MAF/VE hybrid in hybrid mode. We're tuning the entire system.

So Cringer I have to give you credit you're really onto something, and I apologize for my skepticism. You correctly determined that to understand this particular GM MAF/MAP hybrid control scheme one needs to pay attention to Dynamic Airflow. The patent that verlon posted reinforces the Dynamic Airflow method.

Still, I have problems with the implementation. How to determine steady state and how to determine how much each airflow model is corrected?

1) For the first part of determining steady state conditions I haven't seen any quantifiable yes/no. Seems more like qualification, a 'feel' thing, which has no place in an accurate model. That was until verlon provided a patent document that contains a wealth of information. It shows how steady state is determined.

What I propose is a modification to the dynair filter. This will allow more accurate determination of what the control scheme considers steady state, therefore will provide more accurate results.

This is very much pseudocode. Maybe someone who's more competent can translate it to scanner format. Whether or not this matches what's being described in the patent needs verification:

Poll [DynAir] when abs([MAF(k)] - [MAF(k-1)])/[MAF(k-1)] <= [ECM 13432] && abs([MAP(k)]-[MAP(k-1)])/[MAP(k-1)] <= [ECM 13432]
- where k = current time, k-1 = current time - polling rate. So MAF(k) = MAF reading now and MAF(k-1) = MAF reading .250 seconds ago, for example.
- ECM 13432 = Dynamic Airflow Current Gain (0.1)

All it's saying is things are steady state when both MAF and MAP have changed 10% or less. Assumptions are made about k being the polling rate and gain being ECM 13432.

Here's my scribbles on how I came up with the formula.
quick notes.png

2) How to correct airflow models based on dynair. Probably just a matter of using the VE correction factor. Not sure if filter supports 2d arrays, let alone 1D, so It might not be that simple. At least this matter of correcting MAF and VVE should be streamlined assuming (1) is closer to The Truth.

Anyway. Hope this helps.
So am so glad this is finally starting to click!

I think it is important note a few things here.

1) A lot of people people seem to really get hung on the fact that "we don't know if MAF or VVE is informing DynAir at any given moment, therefore we cannot use DynAir."
The fact is, it doesn't matter at all. All we need to know is two things to uncover the true actual airflow:
-Dynamic air
-Fuel trims

On Gen5's there is a PID called Flow Factor that does reveal the weighting between MAF and VVE. This would be nice to have for curiosity sake, but truth is, we don't need it. However, a few days ago I saw this GRG video where Kyle used DynAir in combination with the Flow Factor to come up with a more complex way to tune with DynAir.

2) This entire method is predicated on the fact that DynAir and only DynAir controls IPW. If this can be disproved, then this method is seriously flawed. MAF and VVE only indirectly influence DynAir. It would be totally different if the ECM hopped between MAF, VVE, DynAir at any moment to control IPW. However, DynAir is always present, always updated and always maintained and ready to render an opinion on air flow and is the only controlling factor over the final IPW.

Here is an analogy:
Suppose there are 3 students in math class:
Victor: good at multiplication
Mike: good at division
Dan: who is a cheater and steals answers from Victor and Mike

On the day of the math test whenever Dan sees a multiplication question, he copies Victor's answer. When there is a division question he steals the answer from Mike. When there is a more complex question involving powers (x^2) or square roots, with addition and subtraction, all 3 students are confused. However, Dan must make a decision, so he plays it safe by looking at both Mike and Victor's answer and coming up with something in the middle.

Example:
Test Question #1) 5 * 11 = ?

Victor: 56
Mike: 33
Dan: 56

Dan: 1.7857% high
So the tutor find the answer to question #1 is 55.

Question #2) What is the cube root of 9?
Dan*: 1756
Mike: 4
Victor: 2

*Turns out Dan was day dreaming looking out the window at hot babes walking by and did not copy an answer from either Mike or Victor! However, he still must submit an answer. So he panics and looks at the window again and sees a bus with a serial number drive by and he decides to write down that number.