1
0
Fork 0
mirror of https://github.com/betaflight/betaflight.git synced 2025-07-16 04:45:24 +03:00

Tx buffer availability hack to handle slow devices

This commit is contained in:
jflyper 2016-11-02 00:30:54 +09:00
parent b42de4f2a4
commit 042096fbb7
7 changed files with 70 additions and 33 deletions

View file

@ -67,6 +67,11 @@ int canvasWrite(uint8_t col, uint8_t row, char *string)
return canvasOutput(MSP_CANVAS, (uint8_t *)buf, len + 4);
}
uint16_t canvasTxRoom()
{
return mspSerialPushTxRoom();
}
screenFnVTable_t canvasVTable = {
canvasBegin,
canvasEnd,
@ -74,15 +79,14 @@ screenFnVTable_t canvasVTable = {
canvasWrite,
canvasHeartBeat,
NULL,
canvasTxRoom,
};
void canvasCmsInit(displayPort_t *pPort)
{
pPort->rows = 13;
pPort->cols = 30;
pPort->buftime = 23; // = 256/(115200/10)
pPort->bufsize = 192; // 256 * 3/4 (Be conservative)
pPort->VTable = &canvasVTable;
pPort->vTable = &canvasVTable;
}
void canvasInit()

View file

@ -107,37 +107,45 @@ int8_t lastCursorPos;
void cmsScreenClear(displayPort_t *instance)
{
instance->VTable->clear();
instance->vTable->clear();
instance->cleared = true;
lastCursorPos = -1; // XXX Here
}
void cmsScreenBegin(displayPort_t *instance)
{
instance->VTable->begin();
instance->VTable->clear();
instance->vTable->begin();
instance->vTable->clear();
}
void cmsScreenEnd(displayPort_t *instance)
{
instance->VTable->end();
instance->vTable->end();
}
int cmsScreenWrite(displayPort_t *instance, uint8_t x, uint8_t y, char *s)
{
return instance->VTable->write(x, y, s);
return instance->vTable->write(x, y, s);
}
void cmsScreenHeartBeat(displayPort_t *instance)
{
if (instance->VTable->heartbeat)
instance->VTable->heartbeat();
if (instance->vTable->heartbeat)
instance->vTable->heartbeat();
}
void cmsScreenResync(displayPort_t *instance)
{
if (instance->VTable->resync)
instance->VTable->resync();
if (instance->vTable->resync)
instance->vTable->resync();
}
uint16_t cmsScreenTxRoom(displayPort_t *instance)
{
if (instance->vTable->txroom)
return instance->vTable->txroom();
else
return 10000;
}
void cmsScreenInit(displayPort_t *pDisp, cmsDeviceInitFuncPtr cmsDeviceInitFunc)
@ -377,7 +385,7 @@ void cmsDrawMenu(displayPort_t *pDisplay, uint32_t currentTime)
static uint8_t pollDenom = 0;
bool drawPolled = (++pollDenom % 8 == 0);
int16_t cnt = 0;
int room = cmsScreenTxRoom(pDisplay);
if (!currentMenu)
return;
@ -404,20 +412,26 @@ void cmsDrawMenu(displayPort_t *pDisplay, uint32_t currentTime)
currentCursorPos++;
if (lastCursorPos >= 0 && currentCursorPos != lastCursorPos) {
cnt += cmsScreenWrite(pDisplay, LEFT_MENU_COLUMN, lastCursorPos + top, " ");
room -= cmsScreenWrite(pDisplay, LEFT_MENU_COLUMN, lastCursorPos + top, " ");
}
if (room < 30)
return;
if (lastCursorPos != currentCursorPos) {
cnt += cmsScreenWrite(pDisplay, LEFT_MENU_COLUMN, currentCursorPos + top, " >");
room -= cmsScreenWrite(pDisplay, LEFT_MENU_COLUMN, currentCursorPos + top, " >");
lastCursorPos = currentCursorPos;
}
if (room < 30)
return;
// Print text labels
for (i = 0, p = currentMenu; i < MAX_MENU_ITEMS(pDisplay) && p->type != OME_END; i++, p++) {
if (IS_PRINTLABEL(p)) {
cnt += cmsScreenWrite(pDisplay, LEFT_MENU_COLUMN + 2, i + top, p->text);
room -= cmsScreenWrite(pDisplay, LEFT_MENU_COLUMN + 2, i + top, p->text);
CLR_PRINTLABEL(p);
if (cnt > pDisplay->batchsize)
if (room < 30)
return;
}
}
@ -425,12 +439,12 @@ void cmsDrawMenu(displayPort_t *pDisplay, uint32_t currentTime)
// Print values
// XXX Polled values at latter positions in the list may not be
// XXX printed if the cnt exceeds batchsize in the middle of the list.
// XXX printed if not enough room in the middle of the list.
for (i = 0, p = currentMenu; i < MAX_MENU_ITEMS(pDisplay) && p->type != OME_END; i++, p++) {
if (IS_PRINTVALUE(p)) {
cnt += cmsDrawMenuEntry(pDisplay, p, top + i, drawPolled);
if (cnt > pDisplay->batchsize)
room -= cmsDrawMenuEntry(pDisplay, p, top + i, drawPolled);
if (room < 30)
return;
}
}
@ -494,12 +508,6 @@ long cmsMenuBack(displayPort_t *pDisplay)
return 0;
}
// XXX This should go to device
void cmsComputeBatchsize(displayPort_t *pDisplay)
{
pDisplay->batchsize = (pDisplay->buftime < CMS_UPDATE_INTERVAL) ? pDisplay->bufsize : (pDisplay->bufsize * CMS_UPDATE_INTERVAL) / pDisplay->buftime;
}
// XXX Separation
void cmsx_FeatureRead(void);
void cmsx_FeatureWriteback(void);
@ -528,7 +536,6 @@ void cmsMenuOpen(void)
return;
cmsScreenInit(&currentDisplay, initfunc);
cmsComputeBatchsize(&currentDisplay);
cmsScreenBegin(&currentDisplay);
cmsMenuChange(&currentDisplay, currentMenu);
}

View file

@ -7,6 +7,7 @@ typedef struct screenFnVTable_s {
int (*write)(uint8_t, uint8_t, char *);
int (*heartbeat)(void);
void (*resync)(void);
uint16_t (*txroom)(void);
} screenFnVTable_t;
typedef struct displayPort_s {
@ -14,8 +15,7 @@ typedef struct displayPort_s {
uint8_t cols;
uint16_t buftime;
uint16_t bufsize;
uint16_t batchsize; // Computed by CMS
screenFnVTable_t *VTable;
screenFnVTable_t *vTable;
// CMS state
bool cleared;

View file

@ -783,6 +783,7 @@ screenFnVTable_t displayCmsVTable = {
displayCmsWrite,
NULL,
NULL,
NULL,
};
void displayCmsInit(displayPort_t *pPort)
@ -791,7 +792,7 @@ void displayCmsInit(displayPort_t *pPort)
pPort->cols = 21;
pPort->buftime = 1;
pPort->bufsize = 50000;
pPort->VTable = &displayCmsVTable;
pPort->vTable = &displayCmsVTable;
}
#endif // OLEDCMS

View file

@ -702,6 +702,7 @@ screenFnVTable_t osdVTable = {
osdWrite,
NULL,
max7456RefreshAll,
NULL,
};
void osdCmsInit(displayPort_t *pPort)
@ -709,8 +710,6 @@ void osdCmsInit(displayPort_t *pPort)
shiftdown = masterConfig.osdProfile.row_shiftdown;
pPort->rows = max7456GetRowsCount() - shiftdown;
pPort->cols = 30;
pPort->buftime = 1; // Very fast
pPort->bufsize = 50000; // Very large
pPort->VTable = &osdVTable;
pPort->vTable = &osdVTable;
}
#endif // OSD

View file

@ -246,3 +246,28 @@ void mspSerialPushInit(mspPushCommandFnPtr mspPushCommandFnToUse)
{
mspPushCommandFn = mspPushCommandFnToUse;
}
uint16_t mspSerialPushTxRoom()
{
uint16_t minroom = 50000;
for (uint8_t portIndex = 0; portIndex < MAX_MSP_PORT_COUNT; portIndex++) {
mspPort_t * const mspPort = &mspPorts[portIndex];
if (!mspPort->port) {
continue;
}
// XXX Kludge!!! Avoid zombie VCP port (avoid VCP entirely for now)
if (mspPort->port->identifier == SERIAL_PORT_USB_VCP) {
continue;
}
uint32_t room = mspPort->port->vTable->serialTotalTxFree(mspPort->port);
if (room < minroom) {
minroom = room;
}
}
return minroom;
}

View file

@ -68,3 +68,4 @@ void mspSerialAllocatePorts(void);
void mspSerialReleasePortIfAllocated(struct serialPort_s *serialPort);
void mspSerialPushInit(mspPushCommandFnPtr mspPushCommandFn);
void mspSerialPush(uint8_t, uint8_t *, int);
uint16_t mspSerialPushTxRoom();