Note: This page is deprecated. More info (may) be coming soon to update/replace it.
About LCooler.
I'm writing this to document my vision for the next evolution of the OSD's backend software. Currently, almost all code revolves around the Neuros Cooler, a large-ish C library that contains a number of programming odds and ends, from the Neuros Widgets API to code for reading and writing .INI files. A lot of time and effort has gone into this library, and it would be foolish to simply discard that work. Instead of a wholesale migration, I envision what Lua arguably does best - an integration with the current libraries that requires no changes to existing code but opens up opportunities for dramatic simplification of existing code and elegant integration of new features.
Why Lua?
Two words: Garbage collector.
Of course, that's not the only reason. Aside from the fact that Lua is largely agreed by the community to be the interpreted language of choice for the OSD, Lua's ability to weave in and out of C (or almost any other language) makes it ideal for this kind of "slow replacement" project. It runs very fast for an interpreted language - 5x penalty for fully interpreted code, a number which can get as low as 2x with LuaJIT (which must be ported to the ARM) - and... eh, you're already convinced, aren't you?
Why now?
Clearly it would have been better to pick a course and stick with it for Neuros Cooler; this would mean no time-consuming refactoring. Also, Neuros Cooler isn't blatantly broken. So why bother now?
There are a huge number of halfway compelling reasons for this, and any thinking person can immediately spot a couple of arguments, but for most of them there's an equally compelling counter-argument. All I can say with confidence is this: Our slogan is "The Power of Freedom." LCooler will give casual developers the freedom to program for the OSD without having to deal with a complicated, amorphous C API.
LCooler elements.
Some of these names are pretty ridiculous. I've been accused in the past of being too utilitarian with my naming schemes, so I'm trying something new. We don't have to stick with them!
LuaIPC.
Status: Under development.
The Neuros Interprocess Communication library is a small framework for RPC and callbacks throughout Neuros code. It's currently awaiting review and integration into trunk. If this framework does get deeply embedded into the OSD, APIs for complete control of almost every current feature on the device, from the YouTube browser to the Scheduler, will become available with almost no effort from the developers (seriously, it's like a couple dozen lines of code to expose an entire application over NIPC). LuaIPC is (for now, a client-only) implementation of the RPC and callback mechanism, allowing a Lua application to simply connect to an OSD, load an application's interface, and issue calls as if the API was a native in-process library - even across the Internet.
Content display and interrogation (better widgets).
Status: Design phase, much of Nero's existing Lobster code will be reused.
A next-level wrapper around Neuros Widgets in the cooler. Widgets will become full-fledged Lua objects, allowing you to change their parameters and (for input widgets) interrogate their state more easily. A very simple (as in fast) signals and slots API will be crafted, allowing you to register for certain events, like "focused", "clicked", "value changed", and so on, receiving a callback to a signal handler. The widget will also have a few methods for drawing, such as one that allows you to interrogate its current size.
Widgets will be laid out on the screen in a grid container. The grid is modestly intelligent; it generates a layout based on the widgets it contains with most useful configurations already present, and handles all high-level events for its elements, such as input and focus order. The default grid notably will not support manual focus handling aside from through signals, and layouts cannot be manually specified; if you need it to do something it doesn't, it should be added as a feature. (One exception: There will be a "spacer" widget for creating white space in a grid.) This will make writing GUI applications approximately as difficult and tedious as writing web pages in HTML, and quite possibly even better than that.
The grid itself is a widget, and may be embedded within another grid; a straightforward system to handle events recursively is already designed. Multiple widgets may be bound together in a grid to create a new widget; for example, an IP address widget can be crafted by binding together several boxes. In this case, the grid's default event handler may be overridden, simplifying use of the widget in the containing application.
As much as convenient will be written in pure C, with a Lua wrapper; I hope this one will be too awesome to avoid using everywhere.
Cache and Config.
Status: Design phase.
These two are simply persistent, system-wide, lockable places for storing data that can be accessed easily and are guaranteed to be available, akin to (but more advanced than) the configuration file system currently in use. They're essentially wrappers around Lua tables, but accessor methods must be used to get and store the tables because the underlying method is going to change (initially, the tables will be serialized in /tmp/ and /mnt/OSD/, respectively, and UNIX file locking will be used; later, when Desktop has an embedded Lua interpreter, they'll probably be controlled there, or perhaps in sched). Config is, of course, non-volatile, and cache is volatile; further, the garbage collector will let cache grow to a certain maximum size and no more. This seems obvious and perhaps even redundant, but it's an important design element in many of the tools described below.
Confetti.
Status: Design phase.
The first of hopefully many systems with MVC in mind, the config editor (conf ed -> confetti) will replace the current settings system. A confetti model is merely a Lua table. The syntax is beyond the scope of this document, but it boils down to conveying information like: "Connection Type" is a "listbox" with choices "DHCP" or "Static"; "IP Address" is an "ipaddress", and so forth. Everything else is handled automatically, from layout to fetching and storing values in the global config table.
Any application can use the confetti view library to display any config page within an application, and there will also be a separate configuration application that will allow you to select any config page from a list, much like it is now. It would be trivial to write another configuration app that would work from a web page, from a desktop, from a 770...
As a specific option, the visibility and disabledness of configuration items may depend on the current value of a "listbox" (or whatever we choose to call it) on the same page, or may depend on the value of a Lua expression that gets evaluated on page load.
Cecil.
Status: Design phase.
The content selector (C-SEL -> Cecil) is very similar to one of the many VFS implementations for various desktop environments, except it's a browse-only library. It is loosely MVC. Developers can create a cecil model in C or Lua that implements a few basic functions for walking a tree. The library will use Lua's almost-OO paradigm, so cecil models can be stateful, allowing for more complex features like searching (as on UPnP) or simply for storing the path in the tree. In addition, cecil plugins may at any time request user input from the controller, for things like searching or entering passwords, and may store these values in the config. Cecil models never interact directly with the UI.
As the name implies, the content selector only selects content; it does not play it. "Selecting" content simply means creating a URI that NMSD understands, using the new input plugin infrastructure created for the YouTube browser to handle streaming formats not otherwise supported.
Cecil models are encouraged to use the cache to accelerate their operation; for example, an SMB model may store the list of discovered servers in the cache. More powerful model options, such as building an index of video files from every source, are possible, but will definitely not be in place on the first spin of this library. Both of these suggestions, and many more, can be backgrounded by sched (below).
Sched.
Status: Design phase.
Essentially a cron replacement with some extras. This one will obviously be crafted around the needs of the EPG, but will be somewhat generic, so that ideas like "alarm clock" are a couple lines of code.
Notably, sched will support a couple of mode flags not present in regular cron. "catchup" would run the task if its last scheduled run was missed (good for RSS feeds, et al); "idle" would only run the task if the ARM was under low load (good for things like nightly background indexing of media, or rescanning for network shares every few minutes); "dspidle" would only run if the DSP is not currently being used for encoding, decoding, or whatever; and "dsp" and "tuner" conversely indicate that the task needs control of the DSP or the tuner, respectively.
Clearing these last two would be somewhat interactive; two minutes before the scheduled time, a popup would be displayed that would allow the user to choose to release control or override the scheduled task; if the user releases (or no action is taken) then an IPC call to NMSD would force the release 30 seconds before the scheduled time, leaving ample time for finalization. The user could then take control back during the recording; a popup would warn the user that they were interrupting a backgrounded task that's locking the DSP.
More to come later.

Comments
Post new comment