(get rid of those pseudo options named 'Arguments' in the config file) - replace printf / printf calls by debug / report calls in some drivers - sort and extend LCDd.conf
145 lines
5.0 KiB
Plaintext
145 lines
5.0 KiB
Plaintext
UNDERSTANDING LCDPROC DRIVERS
|
|
|
|
All of the drivers may be activated and compiled in; which is
|
|
activated and used depends on what parameters are given at the command
|
|
line.
|
|
|
|
One can better understand how drivers work by reading the comments
|
|
and documentation in drv_base.h.
|
|
|
|
There is a structure which is used to define all of the command functions
|
|
available from each driver. This command structure is lcd_logical_driver.
|
|
The main use of this structure is for the lcd structure, which contains
|
|
all of the current drivers functions.
|
|
|
|
------------------------------ lcd_logical_driver ------------------------------
|
|
typedef struct lcd_logical_driver {
|
|
int wid, hgt; // size of the LCD in characters
|
|
int cellwid, cellhgt; // size of each LCD char cell in pixels
|
|
char *framebuf; // storage space for display
|
|
|
|
// Functions which might be the same for all drivers...
|
|
|
|
void (*clear) (); // clear screen;
|
|
void (*string) // string at (x,y)
|
|
(int x, int y, char lcd[]);
|
|
|
|
void (*chr) // character at (x,y)
|
|
(int x, int y, char c);
|
|
void (*vbar) // vertical bar at (x,y)
|
|
(int x, int y, int len);
|
|
void (*hbar) // horizontal bar at (x,y)
|
|
(int x, int y, int len);
|
|
void (*init_num) (); //
|
|
void (*num) (int x, int num); // display number
|
|
|
|
// Functions which should probably be implemented in each driver...
|
|
|
|
int (*init) // initialize driver
|
|
(struct lcd_logical_driver * driver, char *args);
|
|
void (*close) (); // close
|
|
void (*flush) (); // flush
|
|
void (*flush_box) // flush box
|
|
(int lft, int top, int rgt, int bot);
|
|
int (*contrast) (int contrast); // set contrast
|
|
void (*backlight) (int on); // set backlight
|
|
void (*output) (int on); // set outputs
|
|
void (*set_char) // set special characters
|
|
(int n, char *dat);
|
|
void (*icon) // set up special icon
|
|
(int which, char dest);
|
|
void (*init_vbar) (); // initialize vertical bar
|
|
void (*init_hbar) (); // initialize horizontal bar
|
|
void (*draw_frame) (); // draw frame
|
|
|
|
char (*getkey) (); // get a key (or 0)
|
|
|
|
char * (*getinfo) (); // get a string of info
|
|
|
|
} Driver;
|
|
------------------------------ lcd_logical_driver ------------------------------
|
|
|
|
The first thing that is done is that lcd_init (lcd.c) is called. This function
|
|
first sets up basic housekeeping details. Then it calls lcd_drv_init, which
|
|
initializes the basic functions for the lcd structure.
|
|
|
|
Each function loops through the list of currently loaded and active drivers.
|
|
The framebuffer is set to point to the appropriate framebuffer. Then
|
|
the function determines what function to call (for each driver) - which
|
|
is one of three possibilities:
|
|
|
|
1. driver->function() > 0
|
|
|
|
Call the driver function contained in driver->function();
|
|
|
|
2. driver->function() == NULL
|
|
|
|
Ignore (no function);
|
|
|
|
3. driver->function() == -1
|
|
|
|
Call the generic driver.
|
|
|
|
The generic driver functions are drv_base_* and are contained in drv_base.c
|
|
|
|
Note that these drv_base_* functions are also installed as part of the "base"
|
|
driver, and thus could be called not only once, but many times.
|
|
|
|
So... to clear the screen (after initializing the drivers) one might do
|
|
this - and it leads to the sequence of activities shown...
|
|
|
|
lcd.clear;
|
|
--> lcd_drv_clear;
|
|
--> driver->clear;
|
|
--> drv_base_clear;
|
|
--> driver->clear;
|
|
--> MtxOrb_clear;
|
|
--> driver->clear;
|
|
--> drv_base_clear;
|
|
--> driver->clear;
|
|
|
|
In the first case, the "base" driver is called. In the second, the "MtxOrb"
|
|
driver is called, and it has a function to use. In the third, an unnamed
|
|
driver is called, but it delegates back to the base function. In the fourth,
|
|
the driver has no function; so it is ignored.
|
|
|
|
SUGGESTED SIMPLIFICATIONS
|
|
|
|
1. Remove the base driver entirely.
|
|
|
|
The base driver does not provide any substantial advantage, and significantly
|
|
complicates code.
|
|
|
|
2. Separate the input driver data from the output driver data.
|
|
|
|
This promotes easier comprehension and allows more specialization of each.
|
|
Some drivers may only have input or output components; some may have both.
|
|
This also permits coding such that only one output device is allowed
|
|
while multiple input devices are allowed.
|
|
|
|
3. Use only ONE output driver for each invocation of the server.
|
|
|
|
This simplifies coding - since there is then only one size, one width, one
|
|
height. It also removes the need for scanning a big loop for functions to
|
|
execute.
|
|
|
|
Given these enhancements, all of drv_base.c could be eliminated, and
|
|
probably most or all of lcd.c. It would dramatically reduce all of the
|
|
processing overhead necessary to handle screen output.
|
|
|
|
MORE SUGGESTIONS AND ENHANCEMENTS
|
|
|
|
1. Make input keys driver-specific.
|
|
|
|
This permits the use of each and every key without overlap. For example,
|
|
it would keep a joystick button press from conflicting with a LCD display
|
|
button.
|
|
|
|
2. Specify the standard (configurable) set of keys for server actions
|
|
in each driver.
|
|
|
|
This permits not only a unique standard configuration for each device,
|
|
it also hides what that is from the program itself. If this is configurable,
|
|
it also makes it possible to adjust this set of keys during operation.
|
|
|