Jump to content

kako mjeriti brzine kotača? Koji algoritam?


Recommended Posts

  • Replies 431
  • Created
  • Zadnji odgovor

Top Posters In This Topic

Evo napravio ubrzanja:

0-60km

0-100km

0-160km

0-200km

i međuubrzanja

60-100km

100-160km

160-200km

100-200km

 

Sad bih još trebao izmjere dužinu impulsa injektora. Najbolji način bi bio uključiti na VEMS onaj port za čuke i digitalno povući. No onda nije univerzalno... Kako najpreciznije izmjeriti dužinu impulsa injektora sa najmanje uzimanja procesorskog vremena? Fire, ideje? :)

Link to comment
Share on other sites

Ma znam, ali dali je toliko potrebna preciznost za mjerenje boččnih sila uprav da se radi o motorsportu?!

 

Nemam pojma. Ovak od oka bih rekao da bi vjerojatno trebao imati točnu drugu decimalu, ali to bi jedino Dominik mogao reći.. :)

Link to comment
Share on other sites

Ako mislis pratiti potrosnju, to ti je malo sjebano za tocno napraviti.

Jer vems prek aim siba van duljinu otvorenosti injektora, a ne kolko bi injektori bili otvoreni da se injektori idealno brzo otvaraju i zatvaraju.

Isti problem ti je kada mjeris kolko otvoreni, jer npr kod mene u leru su oko 1.65ms otvoreni, a od toga je oko 1.1ms dead time. A taj dead time dosta ovisi o naponu akumulatora(znacajno bi se moglo reci).

Pa mozes ovak mjeriti. Slozis si timer neki da je clock tako da ti je tocnost 0.1ms cca. I sada svaki put dok se upali injektor umanjis taj tajmer za cca 11(1.1ms) i stavis da broji. Dok se ugasi injektor ugasis brojenje. I onda dok prede 1s pogledas kolko je taj timer izbrojio i izracunas otprilike potrosnju.

 

btw lpg injektori se brze otvaraju

Link to comment
Share on other sites

Ja sam mislio dići interupt kad se injektor otvori, startati 16bit timer. Dići ponovno interupt kad se injektor zatvori očitati vrijeme timera i stopirati ga...

 

Moram vidjeti jel ATmega128 ima način da to odradi automatiše... :D

 

Znači moram uzeti u obzir i dead time...

 

BTW, što taj AIM može sve izbaciti van? :D

Edited by mr_G
Link to comment
Share on other sites

Evo da ne nabrajam :)

case 0:

return (uint8_t)rtc.sec; //secl

 

case 1:

/* TODO:

check this.

"squirt" is apparently a bitmap of the something:

....BBAAba

where

capital A, B : ????

lowercase a, b: if the given channels are actually squirting

// each squirt_t has its own status field, merge these fields

a = inj_port1.status;

b = inj_port2.status;

 

return ((a & 0x01)

| ((a & 0x06) << 1)

| ((b & 0x01) << 1)

| ((b & 0x06) << 3));

*/

return engine.boostalt_command_duty;

case 2:

// remove the 'idle' bit to avoid confusing mstweak: return (engine.status & (uint8_t)~_BV(idle)); //engine

return engine.status; //engine

 

case 3: return engine.kpa_tps_blend; // AlphaN load; originally sensors8(BARO)

// high resolution MAP

case 4: return engine.kpa250 >> 8;

case 5: return engine.kpa250 & 0xFF;

 

case 6: return engine.mat; //mat

case 7: return engine.coolant; //clt

case 8: return engine.tps; //tps

case 9: return engine.batt; //batt

case 10: // o2

#ifdef WBO2

if (WBO2_SENSOR_CONFIGURED)

{

// traditional stuff via lookup table

// return wbo2.Ip_output;

/* make a concept. Make sure gauge displays 20.9 for 20.9% O2

* eg. gauge means lambda 0.6 .. 5 than O2% between 5..25

* Refer to megatune/vemstune compatible lookup table file

* Test it. DO NOT NEGLECT THESE INSTRUCTIONS.

* Anyone who changes this without the above, most significantly without:

* written concept, working and tested tablefile BOTH for vemstune and megatune

* or if it does not show 20.9 for 20.9% O2, will be prevented from accessing SVN

*/

 

// Andrey's solution, precise values required for AutoTune process possible, and perfect for dataloging

// 20.9 already showed with StallO2 (see PW bytes 16:17), therefore 20.9 not needed to seen here

// MT calcs lambda with simple scale/offset without any lookup tables

// MT vems.ini uses: lambda = {(egoADC + 306)/470}

// So rt_byte_10=164 means lambda = 1.0

uint16_t t16;

t16 = wbo2.current_afr>>5; // 15052 -> 470

if (t16>306){

if (t16<562)

return t16-306; // lambda range is 0.65...1.19

else

return 0xFF;

}else{

return 0;

}

}

else

#endif

return ego_voltage(); //ego

case 11: return mult16_8(corr.ego16,100)>>8; //egocorr

case 12: return corr.air; //aircorr

case 13: return (corr.warm >= 1535) ? 255 : (mult16_8(corr.warm-230,50)>>8); //warmcorr railed to 600%

 

// high resolution RPM

case 14: return engine.rpm_vhr >> 8;

case 15: return engine.rpm_vhr & 0xFF;

 

//show O2 instead pw in meatune for sensor calibration with stalled engine

case 16: return ((engine.rpm==0) && wbo2.current_o2) ? wbo2.current_o2 >> 8 : (inj_port[0].pwcalc >> 8); //pw high

case 17: return ((engine.rpm==0) && wbo2.current_o2) ? wbo2.current_o2 & 0xFF: (inj_port[0].pwcalc & 0xFF); //pw low

case 18: return corr.baro; // barocorr is 128 based

case 19: { // calculate from the stored high-res value (/100 and railing is needed)

uint16_t ge;

ge = mult16_8(corr.gammae381, 68) >> 8;// 381 * 68 / 256 = 101 (NOT 100 !)

 

if ((ge >> 8) != 0) // check for overflow

return 0xFF;

else

return (uint8_t)ge;

}

case 20: return corr.ve_hp;

 

// should we use this style ?

// #define MT_RT_OFFSET_XXX (21)

// #define MT_RT_OFFSET_IGNADV (MT_RT_OFFSET_XXX+1)

 

case 21: return engine.dwell>>4; // 64 usec resolution (possibly but unlikely overflowing)

case 22: return (engine.ignadv < 510 ? (engine.ignadv>>1) : 255); // 128 + ignadv_halfdeg

 

case 23: return iac.position;

 

// make sure 16 bit variables start on even offsets:

 

// raw egt data, do scaling externally (in megatune based on egtofs and egtcal)

case 24: return getMCPdataHIGH(4); // EGT1 HIGH

case 25: return getMCPdataLOW(4); // EGT1 LOW

case 26: return getMCPdataHIGH(3); // EGT2 HIGH

case 27: return getMCPdataLOW(3); // EGT2 LOW

 

// also raw adc data for te other sensors

case 28: return getMCPdataHIGH(6); // EBP HIGH

case 29: return getMCPdataLOW(6); // EBP LOW

case 30: return getMCPdataHIGH(7); // FP HIGH

case 31: return getMCPdataLOW(7); // FP LOW

 

#ifndef KNOCK_ALTERNATIVE

case 32: return getMCPdataHIGH(5); // MISC1 HIGH

case 33: return getMCPdataLOW(5); // MISC1 LOW

case 34: return getMCPdataHIGH(0); // MISC2 HIGH midopa

case 35: return getMCPdataLOW(0); // MISC2 LOW

case 36: return getMCPdataHIGH(1); // MISC3 HIGH midopa

case 37: return getMCPdataLOW(1); // MISC3 LOW

case 38: return getMCPdataHIGH(2); // MISC4 HIGH

case 39: return getMCPdataLOW(2); // MISC4 LOW

#else

case 32:

if (alternative_rtdata()) return knock_cyl[0].knock_adjust;

else return getMCPdataHIGH(5); // MISC1 HIGH

case 33:

if (alternative_rtdata()) return knock_cyl[1].knock_adjust;

else return getMCPdataLOW(5); // MISC1 LOW

case 34:

if (alternative_rtdata()) return knock_cyl[2].knock_adjust;

else return getMCPdataHIGH(0); // MISC2 HIGH midopa

case 35:

if (alternative_rtdata()) return knock_cyl[3].knock_adjust;

else return getMCPdataLOW(0); // MISC2 LOW

case 36:

if (alternative_rtdata()) return knock_cyl[4].knock_adjust;

else return getMCPdataHIGH(1); // MISC3 HIGH midopa

case 37:

if (alternative_rtdata()) return knock_cyl[5].knock_adjust;

else return getMCPdataLOW(1); // MISC3 LOW

case 38:

if (alternative_rtdata()) return knock_cyl[6].knock_adjust;

else return getMCPdataHIGH(2); // MISC4 HIGH

case 39:

if (alternative_rtdata()) return knock_cyl[7].knock_adjust;

else return getMCPdataLOW(2); // MISC4 LOW

#endif

case 40:

{

//#ifdef KNOCK_ALTERNATIVE // Andrey's changes to save CPU time

// MT uses: lambdatarget={256/(latgtADC+200)}

return corr.lambda;

/*#else // old stuff

// MT uses: lambdatarget = { (latgtADC + 71) * 0.00390625}

uint16_t mt_val; mt_val = mult16_8((corr.lambda + LAMBDA_INT_OFFSET), 72) >> 7;

mt_val = (mult16_8(div_65535_x(mt_val), 72) >> 7) - MT_LAMBDA_OFFSET;

return mt_val & 0xFF;

#endif*/

}

 

#ifndef KNOCK_ALTERNATIVE

// dump knock related variables for cylinder 0

case 41: return knock_cyl[0].knock_val >> 8;

case 42: return knock_cyl[0].knock_val & 0xFF;

case 43: return knock_cyl[0].noise_val >> 8;

case 44: return knock_cyl[0].noise_val & 0xFF;

case 45: return knock_cyl[0].knock_adjust;

case 46: return knock_cyl[0].state;

#else

#ifdef CHARGE_TEMP

case 41: return engine.charge_temp;

#endif

#if A340E

case 42: return at_control.at_temp;

#endif

#ifdef TOYOTA_1JZ_VVTI

case 43: return engine.vvt_target;

case 44: return engine.vvt_position;

#endif

#ifndef PS2KEYBOARD

case 45: return engine.revlimit;

#ifdef SECOND_VSS

case 46: return engine.speed1;

#endif

#endif

// case 45: return knock_cyl[0].knock_adjust; // adjust value if retard all

// case 46: return knock_cyl[0].knock_val&0xFC00 ? 0xFF : knock_cyl[0].knock_val >> 2; // knock value if retard all

#endif

 

// status bytes like WBO2 activated and alike

case 47: {

uint8_t status = 0;

#ifdef ALS

if (engine.status_ext & _BV( als_switch_activated )) status |= 0x80; // als switch active

// if (is_als_active()) status |= 0x01; // als function active

#endif

if( engine.status_trig & _BV(n2o_active)) status |= 0x01; // N2O active

#ifdef SOFTLAUNCH

if ( is_launch_input_or_function_active() ) status |= 0x40; // launch control active or launch input button active

#endif

if ( engine.shiftcut_state & ( _BV( IGNCUT_SHIFTCUT ) | _BV( FUELCUT_SHIFTCUT ) )) status |= 0x20; // shift cut

if (engine.status_trig & _BV( injector_staging_active )) status |= 0x10; // inj stage2 active

// if (engine.status & _BV(idle)) status |= 0x08; // idle control

if (config.confswitch & 0x10) status |= 0x08; // Config slot

if (engine.status_ext & _BV(o2_closed_loop)) status |= 0x04; // closed loop (ego)

#ifdef BENCHMARK

if (benchstats.wheel_err & 16) status |= 0x02; // wheel error turn on and off if wheel errors persist

#endif

 

return status;

}

#ifdef BOOSTCONTROL

// without boostcontrol the default 0 will be returned

case 48: return boost_data.boost_target16 >> 5; // 1/8 kPa => 4 kPa

case 49: return engine.boost_command_duty; // boost solenoid duty

case 50: return (uint8_t)((boostcontrol_pid.integral+0x4000)>>7); // boost PID integral, assume PID_INTEGRAL_EXP=6

#endif

case 51: return (uint8_t)(iac.integral>>8)+0x80; // iac.integral, assume INTEGRAL_LIMIT_SCALE=7

case 52: engine.status_ext &= ~_BV(individual_allowed); return engine.sparkcutlvl; // 0 .. 16 ( 0 is no igncut, normal operation)

 

#ifndef KNOCK_ALTERNATIVE

case 53: return individual_power[0];

case 54: return individual_power[1];

case 55: return individual_power[2];

case 56: return individual_power[3];

case 57: return individual_power[4];

case 58: return individual_power[5];

case 59: return individual_power[6];

case 60: engine.status_ext |= _BV(individual_allowed);

if (debug.enable_flags & _BV(7)){

pushfunc(&MTsendRTvar, MT_RTVAR_COUNT);

} //TODO:

return (corr.tpsaccel >= 2040) ? 0xFF: (corr.tpsaccel>>3); //tpsaccel, 4usec => 32 usec ; set back to individual_power[7];

#else

case 53:

if (alternative_rtdata()) return knock_cyl[0].knock_val&0xFC00 ? 0xFF : knock_cyl[0].knock_val >> 2;

else return individual_power[0];

case 54:

if (alternative_rtdata()) return knock_cyl[1].knock_val&0xFC00 ? 0xFF : knock_cyl[1].knock_val >> 2;

else return individual_power[1];

case 55:

if (alternative_rtdata()) return knock_cyl[2].knock_val&0xFC00 ? 0xFF : knock_cyl[2].knock_val >> 2;

else return individual_power[2];

case 56:

if (alternative_rtdata()) return knock_cyl[3].knock_val&0xFC00 ? 0xFF : knock_cyl[3].knock_val >> 2;

else return individual_power[3];

case 57:

if (alternative_rtdata()) return knock_cyl[4].knock_val&0xFC00 ? 0xFF : knock_cyl[4].knock_val >> 2;

else return individual_power[4];

case 58:

if (alternative_rtdata()) return knock_cyl[5].knock_val&0xFC00 ? 0xFF : knock_cyl[5].knock_val >> 2;

else return individual_power[5];

case 59:

if (alternative_rtdata()) return knock_cyl[6].knock_val&0xFC00 ? 0xFF : knock_cyl[6].knock_val >> 2;

else return individual_power[6];

case 60:

engine.status_ext |= _BV(individual_allowed);

if (debug.enable_flags & _BV(7)){

pushfunc(&MTsendRTvar, MT_RTVAR_COUNT);

}

if (alternative_rtdata()) return knock_cyl[7].knock_val&0xFC00 ? 0xFF : knock_cyl[7].knock_val >> 2;

else return individual_power[7];

#endif

case 61: return engine.tok_diff; // this dV/dt will stay

#ifndef PS2KEYBOARD

case 63:

{

uint8_t t8=0;

#ifdef A340E

if (at_control.at_status&_BV(LOCKUP))

t8=100;

#endif

return engine.gear+t8; //gear

}

case 62: return engine.speed; //speed

#else

case 62: return now_64msec() - engine.launchinact_time; //elapsed time

#endif

 

default: return 0;

Link to comment
Share on other sites

Za one koji se kasno uključuju u raspravu, radim na TCM (traction control module) koji će se ponašati i kao g-tech (mjerenje ubrzanja u metrima i km/h) te kao OBC (on board computer) i mjeriti trip times, potrošnju prosječnu, trenutnu, itd...

 

Ima na sebi 4x20 tekstualni display na kojem će se te sve informacije dobiti, s tim da će mjerenje ubrzanja biti:

automatski (čim kreneš on počinje štopati)

ručno (na gumb ako neželiš kočiti do nule nego hoćeš npr 100-200km/h izmjeriti)

 

A kasnije ću razviti i neku aplikaciju u VB koja će za one koji imaju carPC to sve ispisivati na ekranu sa grafikonima, povjesti, best times, itd... :D

 

I naravno primarna stvar oduzimanje momenta na startu kad imaš pretešku nogu.. :lol:

 

Evo kako izgleda hardware u stvarnosti...

 

21072009004.jpg

20022010003h.jpg

20022010o.jpg

Edited by mr_G
Link to comment
Share on other sites

Algoritam radi... Danas izmjerio 7.00s sa lošijim startom.. :D I 4.5s 0-60km/h...

 

Najbolji start mi je bio 3.67s 0-60km/h (ali dalje nisam išao jer smetao promet, što bi izašlo 6.2s 0-100km/h)... :D

 

E sad treba to još sve izbaždariti tako da osim što sve lijepo piše, piše i točno... :D

Link to comment
Share on other sites

Nemoguće je jer to traje manje od 10 sekundi, i toliko mape nisu sjebane...

 

Meni je svaki puta izgorio klip isključivo od previše napora i predugog forsisranja (po 30 sekundi full boost opterećenja i uvijek u šestoj brzini)...

 

Drugi puta nakon 10-tak konstantnih ubrzanja 0-200-0-200-0-200-0-...-0-240...

Link to comment
Share on other sites

Gorane

 

 

JEBO TE EGT DA TE JEBO EGT.

 

Necu ti napisati da si debil idiot ili nesto trece.

 

ALI ZADNJI PUT CU TI RECI JEDNU STVAR I DAJ JU PRIHVATI:

 

 

 

EGT NE ZNACI BAS NISTA JEBO TE ON!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

Link to comment
Share on other sites

Hic. Rekli smo da je kod mene preretardirano paljenje i da je zbog toga i izgorio zadnji motor (previsok EGT). Sad je turbina sa puno boljim kolektorom, malo sam podebljao benzin i imam EGT čukicu...

 

Znači nekakve pojave knocka kod mene zaboravi! Motor jedino može izgoriti od premalo benzina i previsokog EGT...

 

Uspoređivao sam malo EGT na plin i benzin i mogu reći kako je EGT na plin poprilično veći, a u boostu je ono nebo i zemlja razlika...

 

Malo pipnem boost na plin i EGT skače u crveno (1000 stupnjeva)... A kad se sjetim da sam ga ja boostao prije na plin na autoputu! :doh: Nije niti čudo da su oni klipovi bili termički obrađeni i oslabljeni...

 

Plin i turbo motor ne idu zajedno... To je činjenica... Ili barem ako nemaš WI...

Link to comment
Share on other sites

Znas, da te mogu ubit i ne ic u buxu, sad bi ti pucao u koljena, pa u laktove i tako...dok ne krepas u mukama.

 

Nakon toliko tirada ti jos uvijek ne znas kako radi motor i sto to znaci tunirati.

 

Samo cu ti to reci. Sramota.

Link to comment
Share on other sites

Fire, statična kompresija je manja nego prije. A prije je motor odvezao sa istim mapama 1bar tlaka i moje torture preko 5000km... To se baš nebi dogodilo da knocka... :lol:

 

TW jedan od dva koja se mogu naći u XE-u i LET-u... Nije onaj iz NE što je imao Giz... Moj TW ima 6 šarafa a NE ima 3 šarafa... ;) Znači nemam isti TW kao ti.. :D

 

Reci kad možeš da odradimo upgrade i test 0 stupnjeva... ;)

Link to comment
Share on other sites

Please sign in to comment

You will be able to leave a comment after signing in



Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.

Announcements


×
×
  • Create New...