SXXXXXXX_PyBusMonitor1553/cpp/GrifoScope/AvbDdcLegacy/avbddclegacy.cpp
2025-12-17 07:59:30 +01:00

1158 lines
28 KiB
C++

#include "avbddclegacy.h"
#include "avb_driver.h"
//#include <windows.h>
#pragma pack(push)
#pragma pack(4)
#include "TS_drv.h"
#include "Int.h"
#include "VIFunc.h"
#pragma pack(pop)
//#include "time_metrics.h"
//#include <QDebug>
//#define USE_DDC_TIME_TAG_BUFFER
//const avb_1553_message_t avb_frame_end_of_minor__={0};
//const avb_1553_message_t avb_frame_end_of_major__={0};
//const avb_1553_message_t avb_frame_skip_next_message__={0};
#ifdef __GNUC__
#pragma GCC diagnostic ignored "-Wmissing-field-initializers"
#endif
static IAvbDriverClient* avbDriverClient;
static IAvbDriver* avbDriverInstance=0;
static bool sim_rt[32];
extern void DdcSimulator_SimulateBcTick();
extern bool DdcSimulator_isSimulator();
template<typename T_> struct ddc_buffer_map_t
{
enum { max_buff=250 };
typedef T_ value_t;
typedef T_* ptype_t;
T_* db[max_buff];
int add(T_* b)
{
for(int i=3; i<max_buff; ++i)
if (db[i]==b)
return i;
for(int i=3; i<max_buff; ++i)
if (db[i]==0)
{
db[i]=b;
return i;
}
return 0;
}
int set(int pos, T_* b)
{
if (pos>=3 && pos<max_buff)
{
db[pos]=b;
return pos;
}
return 0;
}
T_* fromId(int id)
{
if (id>=3 && id<max_buff)
return db[id];
return 0;
}
int fromDb(T_* b)
{
for(int i=3; i<max_buff; ++i)
if (db[i]==b)
return i;
return 0;
}
};
typedef ddc_buffer_map_t<avb_1553_data_buffer_t> db_map_t;
typedef ddc_buffer_map_t<avb_1553_message_t> msg_map_t;
typedef ddc_buffer_map_t<avb_1553_bc_message_t> frame_map_t;
//avb_1553_bc_message_t avb_1553_end_of_minor_frame;
#define DCALL(x_) (logError( x_ , __LINE__))
static S32BIT bc_isr(Device_p d, S16BIT p1, S16BIT p2);
static S32BIT mon_isr(Device_p d);
typedef union {
uint16_t raw;
struct {
unsigned int wc: 5;
unsigned int sa: 5;
unsigned int tr: 1;
unsigned int rt: 5;
};
CMD idea;
} cw_t;
/*
static CMD cv_cmd(avb_1553_message_t& msg, avb_1553_terminal_t& rt)
{
cw_t tmp;
tmp.wc=msg.wc;
tmp.sa=msg.sa;
tmp.tr=msg.tr ? 1 : 0;
tmp.rt=rt.adr;
return tmp.idea;
}
*/
static CMD ENCODE_CMD(int rt, int tr, int sa, int wc)
{
CMD idea;
idea.subadr=sa;
idea.tadr=rt;
idea.t_r=tr;
idea.wcnt=wc;
return idea;
}
//static DWORD WINAPI ThreadProc(void* param);
typedef struct {
bool niceInterrupt;
bool use_ddc_tt_buffer;
bool debug_msg_level;
unsigned int major_frame_count;
unsigned int major_frame_last_tt;
unsigned int minor_frame_count;
unsigned int minor_frame_last_tt;
unsigned int minor_frame_sequencer;
avb_1553_major_frame_handler_t begin_of_major_frame_handler;
avb_1553_major_frame_handler_t end_of_major_frame_handler;
avb_1553_major_frame_handler_t end_of_minor_frame_handler;
} frame_exec_t;
static volatile frame_exec_t frame_exec;
#define DBG_C(level_, msg_) ({if (frame_exec.debug_msg_level>=level_) {/*avbDriverClient->logError(msg_)/-qDebug()<< msg_ ;*/}})
struct ddc_wrapper_t {
int cardNo;
Device_p pCrd;
DRV_CONFIG dCfg;
CARD_STATE st;
IDEA_INFO info;
Error_t err;
char rtl_ver[1024];
char driver_ver[1024];
char part_no[1024];
char rtl_core_ver[1024];
bool frame_installed;
unsigned num_msg;
frame_map_t fmap;
msg_map_t mmap;
db_map_t bmap;
MESSAGE ddc_msg[256];
U16BIT frameList[1024];
unsigned int bc_served_events;
unsigned int mon_served_events;
unsigned int rt_served_events;
avb_1553_isr_t app_isr;
avb_1553_monitor_isr_t app_mon_isr;
HANDLE hEvent;
HANDLE hTh;
DWORD idThread;
Error_t logError(Error_t e, unsigned int lineno=0)
{
if (!e)
return e;
char buffer[1024];
ddcGetErrorMessage(pCrd, e, buffer);
avbDriverClient->logError("DDC Error: %d = %s @%u", e, buffer, lineno);//qWarning()<<"DDC Error: "<<e<<" "<<buffer;
return e;
}
bool init(int card_num=0)
{
cardNo=card_num;
avbDriverClient->logError("DDC: card=%d", card_num);//qDebug()<<"DDC: "<<"card="<<cardNo;
for(int i=0; i<2; ++i)
{
err=DCALL(ddcResetCard(&pCrd, &dCfg, cardNo));
if (err)
{
IdeaResetCard(cardNo, IDEA_BC_AND_MON);
IdeaShutdown(cardNo);
}
if (!err)
{
avbDriverClient->logError("DDR Reset: %s", dCfg.bcrt_code);
break;
}
}
if (err)
{
IdeaShutdown(cardNo);
return false;
}
info=ddcGetIdeaInfo(pCrd);
avbDriverClient->logError(
"DDC: P/N=%d (%d), driver=%d", info.part_number, info.card_type);
//qDebug()<<"DDC: "<<info.part_number<<" ("<<info.card_type<<"), driver: "<<info.driver_ver<<", selft test ="<<info.self_test;
err=DCALL(ddcIdeaVersion(pCrd, rtl_ver, driver_ver, part_no));
//qDebug()<<"DDC: P/N "<<part_no<<", RTL: "<<rtl_ver<<", Driver: "<<driver_ver;
err|=DCALL(ddcIdeaCoreVersion(pCrd, rtl_core_ver));
avbDriverClient->logError(
"DDC: P/N=%s, driver=%s, rtl=%s (%s)",
part_no, driver_ver, rtl_ver, rtl_core_ver);
//qDebug()<<"DDC: RTL Core Version: "<<rtl_ver;
err|=DCALL(ddcCardState(pCrd, &st));
if (err)
return false;
avbDriverClient->logError(
"DDC: reset state: %d, %d", st.bcrt, st.card);
//qDebug()<<"DDC: State at reset: "<<st.bcrt<<", "<<st.card;
if (st.bcrt!=IDEA_HALTED)
{
//qDebug()<<"DDC: card not HALTED, halting it...";
err=DCALL(ddcHaltIdea(pCrd));
//qDebug()<<"DDC: card halt "<<(err ? "FAILED" : "PASSED");
}
//hEvent=::CreateEvent(0, FALSE, FALSE, 0);
//hTh=::CreateThread(0, 0, ThreadProc, 0, 0, &idThread);
//::SetThreadPriority(hTh, THREAD_PRIORITY_TIME_CRITICAL);
DCALL(ddcDef_int_mask(pCrd, 0xFFFF));
//Error_t(*usr_handler_p)(Device_p, S16BIT, S16BIT) =
// (Error_t(*)(Device_p, S16BIT, S16BIT)) bc_isr;
err=DCALL(ddcSetBCRTEvent(pCrd, bc_isr)); //(Error_t (* __DECL)(Device_p, S16BIT, S16BIT))bc_isr));
err=DCALL(ddcSetMONEvent(pCrd, mon_isr));
err=DCALL(ddcDef_monitor_stack(pCrd, CYCLIC_STACK));
err=DCALL(ddcSelect_bus(pCrd, YES, YES));
//DCALL(ddcSetRespTimeout(pCrd, 20));
return err==0;
}
unsigned int getRunState()
{
DCALL(ddcCardState(pCrd, &st));
return st.card;
}
void setMinorFrameTime(S32BIT time)
{
avbDriverClient->logError("DDC: MF time=%u", time);
//qDebug()<<"MF Time:"<<time;
err=DCALL(ddcDef_minor_frame_time(pCrd, time));
}
int go_bc(int times)
{
avbDriverClient->logError("DDC: GO BC");
DCALL(ddcHalt_bcrt(pCrd));
DCALL(ddcDef_int_mask_bcrt(pCrd, ~ ((1<<4)|(1<<5)|(1<<6)|(1<<7))));
//DCALL(ddcDef_int_mask_bcrt(pCrd, ~ ((1<<4)|(1<<5)|(1<<6))));
//qDebug()<<"DDC: run Bc...";
DCALL(ddcRun_bc(pCrd, 1, times<1 ? IDEA_FOREVER : times));
DCALL(ddcCardState(pCrd, &st));
avbDriverClient->logError(
"DDC: reset state: %d, %d", st.bcrt, st.card);
enableSkipMessage(true);
if (DdcSimulator_isSimulator())
{
for(int i=1; i<31; ++i)
DCALL(ddcSet_busy(pCrd, i, NO));
}
//DCALL(ddcRun_rt(pCrd));
return err;
}
int go_mon()
{
//return 0;
avbDriverClient->logError("DDC: GO MON");
if (app_mon_isr)
ddcDef_int_mask_monitor(pCrd, ~ (1<<14));
else
ddcDef_int_mask_monitor(pCrd, ~0);
//qDebug()<<"DDC: run Mon...";
err=DCALL(ddcRun_mon(pCrd));
return err;
}
int halt_mon()
{
avbDriverClient->logError("DDC: Halt MOM");
ddcDef_int_mask_monitor(pCrd, ~0);
//qDebug()<<"DDC: HaltMon";
err=DCALL(ddcHalt_mon(pCrd));
return err;
}
int halt_bc()
{
avbDriverClient->logError("DDC: Halt BC");
//qDebug()<<"DDC: HaltBcRt";
DCALL(ddcDef_int_mask_bcrt(pCrd, ~0));
err=DCALL(ddcHalt_bcrt(pCrd));
halt_mon();
return err;
}
int stop()
{
//qDebug()<<"DDC: HaltIdea";
avbDriverClient->logError("DDC: stop");
err=DCALL(ddcHaltIdea(pCrd));
return err;
}
void write_mode_data(unsigned int ta, unsigned int mode, avb_1553_word_t w)
{
DCALL(ddcWrite_mode_data(pCrd, ta, mode, w));
}
void enableSkipMessage(bool enable=true)
{
//avbDriverClient->logError("DDC: SKIP=%s", enable ? "ENA" : "DIS");
//DCALL(ddcSkip_next_message(pCrd, enable ? IDEA_NO : IDEA_YES));
}
void checkIntrStatus(avb_1553_intr_status_t& sts)
{
//ViInt32 i_tot, i_mon_host, i_mon_card, i_bc_host, i_bc_card;
//IdeaDbgOSGetCounts(cardNo, &i_tot, &i_mon_host, &i_mon_card, &i_bc_host, &i_bc_card);
sts.raised=bc_served_events; //i_bc_card;
sts.served=bc_served_events;
}
void shutdown()
{
if (pCrd)
{
ddcHaltIdea(pCrd);
ddcShutDownIdea(&pCrd);
pCrd=0;
}
}
~ddc_wrapper_t()
{
shutdown();
}
};
static ddc_wrapper_t ddc_cx;
static unsigned long tt_base=0;
//metricRegistered metricDdcDriverISR("DRV1553");
#define mISR metricDdcDriverISR
//static metricRegistered mISRMON("DDC_MON_ISR", 0, 0, &mISR);
//static metricRegistered mISRSched("DDC_BC_SCHED", 0, 0, &mISR);
//static metricRegistered mISRSUnknown("DDC_BC_UNKNOW", 0, 0, &mISR);
static unsigned int tt_synch_fpos;
static void bc_schedule_nice_interrupt(Device_p d)
{
//metricMeasure xx(mISRSched);
if (frame_exec.minor_frame_sequencer>9999)
return;
//++frame_exec.minor_frame_sequencer;
for(; frame_exec.minor_frame_sequencer<250; ++frame_exec.minor_frame_sequencer)
{
U16BIT type=0x0080;
U16BIT subtype=ddc_cx.frameList[frame_exec.minor_frame_sequencer];
if (subtype==END_OF_MAJOR)
{
frame_exec.minor_frame_sequencer=10000;
break;
}
else if (subtype==END_OF_MINOR)
{
++frame_exec.minor_frame_sequencer;
break;
}
if (subtype==tt_synch_fpos)
continue;
{
MESSAGE m;
Error_t sts=ddcRead_message(ddc_cx.pCrd, subtype, &m);
if (sts)
continue;
if (m.det_error!=NO_ERROR)
{
if (m.det_error==BIT_LIT_IN_STATUS)
type=0x82;
else
type=0x81;
}
S16BIT itype=type | (subtype<<8);
S16BIT param=0;
bc_isr(d, itype, param);
}
}
}
static S32BIT bc_isr(Device_p d, S16BIT itype, S16BIT /*param*/)
{
//metricMeasure xx(mISR);
U16BIT type=itype & 0x00FF;
U16BIT subtype=(itype>>8) & 0x00FF;
switch(type)
{
case 0x83:
switch(subtype)
{
case 0x00FE: //end of major
//++frame_exec.major_frame_count;
subtype=1;
break;
case 0x00FF: //end of minor
//++frame_exec.minor_frame_count;
subtype=2;
break;
}
case 0x80: //succ. message
case 0x81: //comm. error
case 0x82: //bit set status
++ddc_cx.bc_served_events;
if (subtype==1)
{
++frame_exec.major_frame_count;
frame_exec.minor_frame_count=0;
frame_exec.minor_frame_sequencer=0;
U32BIT tt_val;
if (frame_exec.use_ddc_tt_buffer)
{
static U32BIT tt_buff[256];
S16BIT tt_count;
Error_t sts=ddcRead_time_tags(ddc_cx.pCrd, tt_buff, &tt_count);
if (sts==0 && tt_count>0)
tt_val=tt_buff[0];
else
ddcRead_mon_rtc(ddc_cx.pCrd, &tt_val);
}
else
ddcRead_mon_rtc(ddc_cx.pCrd, &tt_val);
frame_exec.major_frame_last_tt=tt_val;
if (frame_exec.begin_of_major_frame_handler)
frame_exec.begin_of_major_frame_handler(avbDriverInstance, frame_exec.major_frame_count, tt_val);
}
else if (subtype==2)
{
U32BIT tt_val;
ddcRead_mon_rtc(ddc_cx.pCrd, &tt_val);
frame_exec.minor_frame_last_tt=tt_val;
++frame_exec.minor_frame_count;
if (frame_exec.niceInterrupt)
bc_schedule_nice_interrupt(d);
if (frame_exec.end_of_minor_frame_handler)
frame_exec.end_of_minor_frame_handler(avbDriverInstance, frame_exec.minor_frame_count, tt_val);
}
else
{
avb_1553_message_t* msg=ddc_cx.mmap.fromId(subtype);
U32BIT tt_val;
ddcRead_mon_rtc(ddc_cx.pCrd, &tt_val);
if (msg->sa==0)
{
{
tt_base=tt_val;
break;
}
}
if (msg)
{
bool ok= (type==0x80);
if (msg->msgHandler)
msg->msgHandler(avbDriverInstance, ok, msg, tt_val);
}
}
break;
default:
{
//metricMeasure xx(mISRSUnknown);
}
break;
}
return 0;
}
static S32BIT mon_isr(Device_p /*d*/)
{
//metricMeasure xx(mISRMON);
++ddc_cx.mon_served_events;
if (ddc_cx.app_mon_isr)
ddc_cx.app_mon_isr(0);
return 0;
}
class AvbDDCDriver: public IAvbDriver
{
public:
AvbDDCDriver()
{
ddc_cx.init();
}
virtual ~AvbDDCDriver()
{
ddc_cx.shutdown();
}
virtual bool initialize()
{
return false;
}
virtual avb_1553_intr_status_t getIntrStatus()
{
avb_1553_intr_status_t sts;
ddc_cx.checkIntrStatus(sts);
sts.major_frames=frame_exec.major_frame_count;
sts.major_frame_tt=frame_exec.major_frame_last_tt;
return sts;
}
virtual bool go(int times)
{
if (!ddc_cx.frame_installed)
{
installFrame();
}
//return false;
bool ok=ddc_cx.go_bc(times)==0;
static U32BIT tt_history[512];
S16BIT n=0;
avbDriverClient->logError("Clearinng tt queue");
ddc_cx.logError(ddcRead_time_tags(ddc_cx.pCrd, tt_history, &n), 0);
return ok;
}
virtual bool stop()
{
ddc_cx.halt_mon();
return ddc_cx.halt_bc()==0;
}
virtual bool shutdown()
{
ddc_cx.stop();
ddc_cx.shutdown();
return true;
}
virtual bool go_mon()
{
return ddc_cx.go_mon()==0;
}
virtual bool halt_mon()
{
return ddc_cx.halt_mon()==0;
}
virtual bool setUpMessages(unsigned int /*num_of_message*/, const avb_1553_message_t *const /*msg_table*/)
{
return false;
}
unsigned int calcTime(unsigned t, unsigned int wc)
{
if (t)
return t;
return (wc+4)*20+25;
}
avb_1553_bc_frame_t* xframe;
virtual bool setUpBcFrame(avb_1553_bc_frame_t& frame)
{
xframe=&frame;
installFrame();
return true;
}
bool installFrame()
{
static INJ_ERR kInjErr;
static MESSAGE msgBeginOfFrame;
static MESSAGE msgBeginOfFrame_tt={IDEA_NOP, ENCODE_CMD(1, 0, 1, 1), ENCODE_CMD(1, 0, 1, 1), 50, 1, 1, IDEA_BUS_A, IDEA_IMR_TIME_TAG, IDEA_IMR_INT_ON_END_OF_MESSAGE, &kInjErr};
static MESSAGE msgBeginOfFrame_nott={IDEA_NOP, ENCODE_CMD(1, 0, 1, 1), ENCODE_CMD(1, 0, 1, 1), 50, 1, 1, IDEA_BUS_A, IDEA_IMR_NO_OPERATION, IDEA_IMR_INT_ON_END_OF_MESSAGE, &kInjErr};
avb_1553_bc_frame_t& frame=*xframe;
if (frame_exec.use_ddc_tt_buffer)
msgBeginOfFrame=msgBeginOfFrame_tt;
else
msgBeginOfFrame=msgBeginOfFrame_nott;
static MESSAGE msgEndOfMinor={IDEA_NOP, ENCODE_CMD(1, 0, 1, 1), ENCODE_CMD(1, 0, 1, 1), 50, 1, 1, IDEA_BUS_A, IDEA_IMR_NO_OPERATION, IDEA_IMR_INT_ON_END_OF_MESSAGE, &kInjErr};
ddc_cx.num_msg=0;
unsigned int N=frame.num_of_message;
bool end_of_major_find=false;
for(int i=0; i<32; ++i)
sim_rt[i]=0;
ddc_cx.logError(ddcDef_message(ddc_cx.pCrd, 1, &msgBeginOfFrame));
ddc_cx.logError(ddcDef_message(ddc_cx.pCrd, 2, &msgEndOfMinor));
ddc_cx.frameList[0]=1;
unsigned int fpos=0;
if (frame.minor_frame_time<10000)
frame.minor_frame_time=10000;
//frame.minor_frame_time=20000;
for(unsigned int i=0; i<N; ++i, ++fpos)
{
avb_1553_bc_message_t* bc_msg_p=frame.msg[i];
if (!bc_msg_p)
break;
++ddc_cx.num_msg;
avb_1553_bc_message_t& bc_msg=*bc_msg_p;
avb_1553_message_t* msg=bc_msg.msg;
if (msg==avb_frame_end_of_minor)
{
avbDriverClient->logError("DDC: %u: END OF MINOR",i);//DBG_C(1, "F["<<i<<"] END OF MINOR");
//ddc_cx.frameList[fpos]=2;
//++fpos;
//++ddc_cx.num_msg;
ddc_cx.frameList[fpos]=IDEA_END_OF_MINOR;
continue;
}
if (msg==avb_frame_end_of_major)
{
avbDriverClient->logError("DDC: %u(%u): END OF MAJOR",i, fpos);//DBG_C(1,"F["<<fpos<<"] END OF MAJOR");
//ddc_cx.frameList[fpos]=2;
//++fpos;
//++ddc_cx.num_msg;
ddc_cx.frameList[fpos]=IDEA_END_OF_MAJOR;
end_of_major_find=true;
continue;
}
int bc_i=ddc_cx.fmap.fromDb(&bc_msg);
if (bc_i)
{
avbDriverClient->logError("DDC: %u(%u): F[%u]",i, fpos, bc_i );//DBG_C(1,"F["<<fpos<<"]="<<bc_i);
ddc_cx.frameList[fpos]=bc_i;
continue;
}
bc_i=ddc_cx.fmap.add(&bc_msg);
bc_msg.avbReserved_=bc_i;
bc_msg.avbReserved_BcPos=fpos;
MESSAGE& dm=ddc_cx.ddc_msg[bc_i];
ddc_cx.frameList[fpos]=bc_i;
//avbDriverClient->logError("DDC: %u(%u): M[%u] %s: %u:%u:%u:%u",i, fpos, bc_i, msg->nickName, dm.cmd_1.tadr, dm.cmd_1.subadr, dm.cmd_1.t_r, dm.cmd_1.wcnt );//DBG_C(1,"F["<<fpos<<"] NEW MESSAGE: "<<bc_i<<" "<<msg->nickName);
memset(&dm, 0, sizeof dm);
dm.inj_error_ptr=&kInjErr;
dm.first_intermessage_routine=IDEA_IMR_NO_OPERATION;
dm.second_intermessage_routine=IDEA_IMR_NO_OPERATION;
//bc_msg.interrupt=avb_bc_interrupt;
dm.first_intermessage_routine=(msg->type==avb_t_nop_skip_next) ? IDEA_IMR_SKIP_NEXT : IDEA_IMR_NO_OPERATION;
dm.second_intermessage_routine=bc_msg.interrupt ? IDEA_IMR_INT_ON_END_OF_MESSAGE : IDEA_IMR_NO_OPERATION;
if (msg->sa==0)
{
dm.first_intermessage_routine=IDEA_IMR_TIME_TAG;
dm.second_intermessage_routine=IDEA_IMR_INT_ON_END_OF_MESSAGE;
tt_synch_fpos=fpos;
//ddc_cx.frameList[fpos]=2000;
}
if (!msg || !msg->target)
{
DBG_C(1,"M["<<bc_i<<"] IDEA NOP");
dm.comm_type=IDEA_NOP;
dm.time_to_next_message=calcTime(bc_msg.time_to_next, 10);
dm.cmd_1.subadr=1;
dm.cmd_1.tadr=1;
dm.cmd_1.wcnt=10;
dm.cmd_1.t_r=0;
dm.cmd_2=dm.cmd_1;
continue;
}
if (msg->msgHandler && !frame_exec.niceInterrupt)
dm.second_intermessage_routine=IDEA_IMR_INT_ON_END_OF_MESSAGE;
dm.cmd_1.subadr=msg->sa;
dm.cmd_1.tadr=msg->target->adr; //msg->tr==avb_tx ? msg->src->adr : msg->dst->adr;
dm.cmd_1.t_r=msg->tr==avb_tx ? 1 : 0;
dm.cmd_1.wcnt=msg->wc>=32 ? 0 : msg->wc;
dm.cmd_2=dm.cmd_1;
if (msg->target->mode==avb_term_simulated)
sim_rt[msg->target->adr]=true;
if (msg->target->mode==avb_term_disabled || msg->type==avb_t_nop || msg->type==avb_t_nop_skip_next)
dm.comm_type=IDEA_NOP;
else
dm.comm_type=(msg->sa==0 || msg->sa==31) ? IDEA_MODE : ( (msg->tr==avb_tx) ? TRANSMIT : RECEIVE);
dm.time_to_next_message=calcTime(bc_msg.time_to_next, msg->wc);
dm.bus=bc_msg.bus==avb_bus_B ? BUS_B : BUS_A;
//DBG_C(1, "M["<<bc_i<<"] ct="<<dm.comm_type<<" CMD1: "<<dm.cmd_1.tadr<<"-"<<dm.cmd_1.t_r<<"-"<<dm.cmd_1.subadr<<"-"<<dm.cmd_1.wcnt);
avbDriverClient->logError("DDC: %u(%u): M[%u] %s: %u %u:%u:%u:%u",i, fpos, bc_i, msg->nickName, dm.comm_type, dm.cmd_1.tadr, dm.cmd_1.subadr, dm.cmd_1.t_r, dm.cmd_1.wcnt );//DBG_C(1,"F["<<fpos<<"] NEW MESSAGE: "<<bc_i<<" "<<msg->nickName);
int msg_i=ddc_cx.mmap.fromDb(msg);
if (msg_i)
{
//qDebug()<<"M["<<bc_i<<"] DB: "<<msg_i;
avbDriverClient->logError("DDC: defMsg: %u, %u", msg_i,bc_i);
dm.data_table_no=msg_i;
dm.last_data_table_no=dm.data_table_no;
ddc_cx.logError(ddcDef_message(ddc_cx.pCrd, bc_i, &dm));
continue;
}
msg_i=ddc_cx.mmap.add(msg);
msg->avbReserved_=msg_i;
msg->avbReserved_BcPos=fpos;
DBG_C(1,"M["<<bc_i<<"] NEW DB: "<<msg_i<<" size="<<msg->wc);
avbDriverClient->logError("DDC: newMsg: %u, %u", msg_i,bc_i);
ddc_cx.logError(ddcDef_table_size(ddc_cx.pCrd, msg_i, msg->wc));
dm.data_table_no=msg_i;
dm.last_data_table_no=msg_i;
ddc_cx.logError(ddcDef_message(ddc_cx.pCrd, bc_i, &dm));
}
if (true || !end_of_major_find)
{
ddc_cx.frameList[ddc_cx.num_msg]=IDEA_END_OF_MINOR; //2;
++ddc_cx.num_msg;
ddc_cx.frameList[ddc_cx.num_msg]=IDEA_END_OF_MAJOR;
++ddc_cx.num_msg;
}
//++ddc_cx.num_msg; //the default major frame begin message
ddc_cx.setMinorFrameTime(frame.minor_frame_time);
//DBG_C(0,"Def Frame: "<<ddc_cx.num_msg);
//for(unsigned int n=0; n<ddc_cx.num_msg; ++n)
// DBG_C(1," "<<n<<": "<<ddc_cx.frameList[n]);
avbDriverClient->logError("DDC: frame: %u, mt=%u", ddc_cx.num_msg, frame.minor_frame_time);
//for(unsigned int n=0; n<ddc_cx.num_msg; ++n)
// avbDriverClient->logError(" [%d]=%d", n, ddc_cx.frameList[n]);
ddc_cx.logError(ddcDef_frame(ddc_cx.pCrd, ddc_cx.num_msg, ddc_cx.frameList));
ddc_cx.setMinorFrameTime(frame.minor_frame_time);
for(int i=1; i<30; ++i)
if (false && sim_rt[i])
{
static RT_DEFS rt;
rt.inj_error=&kInjErr;
ddc_cx.logError(ddcDef_emulate_rt(ddc_cx.pCrd, i, IDEA_YES));
ddc_cx.logError(ddcDef_rt(ddc_cx.pCrd, i, &rt));
}
else
ddc_cx.logError(ddcDef_emulate_rt(ddc_cx.pCrd, i, IDEA_NO));
ddc_cx.frame_installed=true;
if (0)
{
static RT_DEFS rt;
rt.inj_error=&kInjErr;
ddc_cx.logError(ddcDef_emulate_rt(ddc_cx.pCrd, 0x3, IDEA_YES));
ddc_cx.logError(ddcDef_rt(ddc_cx.pCrd, 3, &rt));
}
ddcDef_emulate_bc(ddc_cx.pCrd, 0x1c, IDEA_NO);
return true;
}
run_status_t getRunState()
{
switch(ddc_cx.getRunState())
{
default:
return sts_halt;
case RUN_BCRT_MONITOR_STATE:
return sts_bc_mon_run;
case RUN_MONITOR_STATE:
return sts_mon_run;
case RUN_BCRT_STATE:
return sts_bc_run;
}
}
void set_isr(avb_1553_isr_t isr)
{
ddc_cx.app_isr=isr;
}
void set_mon_isr(avb_1553_monitor_isr_t isr)
{
ddc_cx.app_mon_isr=isr;
}
void enableMonitorIsr(bool enable)
{
if (enable)
ddcDef_int_mask_monitor(ddc_cx.pCrd, ~(1<<14));
else
ddcDef_int_mask_monitor(ddc_cx.pCrd, 0xFFFF);
}
bool getMonitorRawBuffer(avb_1553_monitor_info_t *const b)
{
//return false;
static S16BIT buffer[64*1024];
S16BIT count=(S16BIT)sizeof(buffer)/sizeof(S16BIT);
S16BIT messages=sizeof(buffer)/(40*sizeof(S16BIT));
ddc_cx.err=ddc_cx.logError(ddcRead_mon_stack_part(ddc_cx.pCrd, buffer, &count, &messages));
if (!b)
return false;
b->size=count;
b->buffer=(avb_1553_word_t*)buffer;
if (ddc_cx.err)
return false;
return true;
}
void writeSyncWord(avb_1553_word_t w) override
{
//DCALL(ddcWrite_mode_data(ddc_cx.pCrd, 0, 17, w));
avbDriverClient->logError("DDC: SynchW=%X", w);
ddc_cx.write_mode_data(0x1c/*0*/, 17, w);
//if (w==0)
// ddcSet_rtc(ddc_cx.pCrd, 0);
}
bool insertMessage(const avb_1553_bc_message_t* const m)
{
//avbDriverClient->logError("DDC: Insert message: %d", m->avbReserved_BcPos);
//ddc_cx.logError(ddcInsert_message(ddc_cx.pCrd, m->avbReserved_BcPos+1));
return true;
}
bool enableSkipMessage(bool enable)
{
ddc_cx.enableSkipMessage(enable);
return true;
}
int getLastDriverError()
{
return ddc_cx.err;
}
const char* getDriverErrrorMessage(int /*error_code*/)
{
static char tmp[1024];
ddcGetErrorMessage(ddc_cx.pCrd, ddc_cx.err, tmp);
return tmp;
}
bool mon_decode_msg(avb_1553_mon_decoded_t * const decoded, void * const buffer)
{
MON_MSG msg;
memset(decoded, 0, sizeof *decoded);
Error_t err=ddcDecode_mon_message(ddc_cx.pCrd, (U16BIT*)buffer, &msg);
if (err)
return false;
bool c1=msg.comm_type==RECEIVE || msg.comm_type==MODE || msg.error_inf.illegal==YES;
decoded->invalid=msg.error_inf.illegal==YES;
decoded->modecode=msg.comm_type==MODE;
decoded->bus=msg.bus==BUS_A ? 0 : 1;
decoded->broadcast=msg.broadcast==YES;
decoded->cmd.raw=c1 ? msg.cmd_1 : msg.cmd_2;
decoded->rx_sts_received=msg.stat_r_flag==1;
decoded->tx_sts_received=msg.stat_t_flag==1;
decoded->sts.raw=c1 ? msg.rx_status : msg.tx_status;
decoded->rtrt_tx_cmd.raw=!c1 ? msg.cmd_1 : msg.cmd_2;
decoded->rtrt_tx_sts.raw=!c1 ? msg.rx_status : msg.tx_status;
//decoded->data=(avb_1553_word_t*)msg.data_buf;
decoded->next=msg.next_msg;
decoded->timetag=msg.rtc;
decoded->wc=msg.word_count;
for(int w=0; w<msg.word_count; ++w)
decoded->data[w]=(avb_1553_word_t)msg.data_buf[w];
decoded->rt=c1 ? msg.s_cmd_1.tadr : msg.s_cmd_2.tadr;
decoded->err=msg.error==YES ? true : false;
decoded->sa=c1 ? msg.s_cmd_1.sadr : msg.s_cmd_2.sadr;
decoded->tr=c1 ? msg.s_cmd_1.tr : msg.s_cmd_2.tr;
decoded->internal_eror_code=msg.error_inf.code;
if (decoded->err)
{
decoded->no_response=msg.error_inf.type==TYPE_NO_RESPONSE;
decoded->bit_in_status_err=msg.error_inf.tx_status!=NO_ERROR || msg.error_inf.tx_status!=NO_ERROR;
}
return true;
}
virtual void simulateBcTick()
{
DdcSimulator_SimulateBcTick();
}
virtual bool readDataBuffer(avb_1553_message_t* const msg, void* const dst, unsigned int wc)
{
if (wc>32)
return false;
S16BIT w= (S16BIT) ((wc==0) ? msg->wc : wc);
ddcRead_data(ddc_cx.pCrd, msg->avbReserved_, (S16BIT*)dst, w);
return true;
}
virtual bool writeDataBuffer(const avb_1553_message_t* const msg, void* const src, unsigned int wc=0)
{
if (wc>32)
return false;
S16BIT w= (S16BIT) ((wc==0) ? msg->wc : wc);
ddcWrite_data(ddc_cx.pCrd, msg->avbReserved_, (S16BIT*)src, w, 1);
return true;
}
virtual void set_begin_of_major_frame_handler(avb_1553_major_frame_handler_t handler)
{
frame_exec.begin_of_major_frame_handler=handler;
}
virtual void set_minor_frame_handler(avb_1553_major_frame_handler_t handler)
{
frame_exec.end_of_minor_frame_handler=handler;
}
virtual void set_end_of_frame_handler(avb_1553_major_frame_handler_t handler)
{
frame_exec.end_of_major_frame_handler=handler;
}
virtual avb_microseconds_t getTimetag()
{
//static U32BIT tt_base=0;
U32BIT tt_val;
#if 0
static U32BIT tt_history[128];
S16BIT n=8;
ddc_cx.logError(ddcRead_time_tags(ddc_cx.pCrd, tt_history, &n), 0);
if (n)
{
tt_base=tt_history[0];
avbDriverClient->logError("DDC TBASE=%d", tt_base);
}
#endif
ddcRead_mon_rtc(ddc_cx.pCrd, &tt_val);
tt_val-=tt_base;
return tt_val;
}
virtual void niceInterrupt(bool enable)
{
frame_exec.niceInterrupt=enable;
}
virtual const char* getDeviceName()
{
return ddc_cx.part_no;
}
virtual bool isSimulator() const
{
return DdcSimulator_isSimulator();
}
};
IAvbDriver* AvbDriverCreate(const char* /*subtype*/,IAvbDriverClient* client)
{
avbDriverClient=client;
frame_exec.niceInterrupt=true;
frame_exec.use_ddc_tt_buffer=false;
if (avbDriverInstance==0)
{
avbDriverInstance=new AvbDDCDriver;
}
return avbDriverInstance;
}
#if 0
#include <QSettings>
IAvbDriver* Avb_DriverCreate(QSettings *settings)
{
frame_exec.niceInterrupt=true;
avbDriverInstance=new AvbDDCDriver;
if (settings)
{
settings->beginGroup("avbDriver_DDC");
QVariant tmp=settings->value("niceInterrupts");
if (tmp.isValid())
{
frame_exec.niceInterrupt=tmp.toBool();
}
tmp=settings->value("USE_DDC_TIME_TAG_BUFFER");
if (tmp.isValid())
{
frame_exec.use_ddc_tt_buffer=tmp.toBool();
}
tmp=settings->value("DDC_DEBUG_MSG_LEVEL");
if (tmp.isValid())
frame_exec.debug_msg_level=tmp.toInt();
settings->endGroup();
}
qDebug()<<"[DDC] niceInterrups="<<frame_exec.niceInterrupt<<", use_tt_buff="<<frame_exec.use_ddc_tt_buffer;
return avbDriverInstance;
}
IAvbDriver::~IAvbDriver()
{
}
AvbDdcLegacy::AvbDdcLegacy()
{
}
#endif