This topic describes how to port a legacy C code app running on POSIX/Linux. Instructions describe how to get an app running on Legato and use pre-built APIs to access services like SMS, SIM, voice calling, and data connections.
With this method you don't have to rewrite the app to use Legato event loops, auto-generated main() functions, etc.
Convert App to Legato
1. Build a legacy app executable for a target using the cross toolchain provided:
$ /opt/swi/y16-ext/sysroots/x86_64-pokysdk-linux/usr/bin/arm-poky-linux-gnueabi/arm-poky-linux-gnueabi-gcc -o legacyProgram main.c $
2. Copy the legacy app executable onto the target using a tool like scp:
$ scp legacyProgram 192.168.1.2:
legacyProgram 100% 9366 9.2KB/s 00:00
$
3. Run the legacy app from the target command-line:
root@swi-mdm9x15:~# ./legacyProgram
Hello world.
root@swi-mdm9x15:~#
Create Definition Files
1. Use Legato's application life cycle management features by creating an .adef file that bundles the cross-compiled executable into an application:
legacyProgram.adef
sandboxed: false
bundles:
{
file:
{
[x] legacyProgram /bin/
}
}
processes:
{
run:
{
( legacyProgram )
}
}
2. Run mkapp to generate an application bundle for your target:
$ mkapp -t wp7 legacyProgram.adef
$
3. Install the app bundle on the target using instapp:
$ instapp legacyProgram.wp7
Installing application 'legacyProgram' from file 'legacyProgram.wp7'.
Installing app 'legacyProgram'...
Created user 'applegacyProgram' (uid 1011, gid 1011).
DONE
$
4. From the target's command line, use app start to run the program:
root@swi-mdm9x15:~# app start legacyProgram Starting app 'legacyProgram'...
Hello world.
DONE
root@swi-mdm9x15:~#
Use Modem Services
Here is how to use a Legato modem service API (e.g., le_info):
1. #include legato.h and interfaces.h.
2. Connect to the service by calling le_info_ConnectService(). At runtime, if the le_info service isn't up, this will block until it comes up. In the meantime, you'll see your app in the WAITING CLIENTS list if you run sdir list.
3. Add a call to one of the le_info API functions (e.g., le_info_GetDeviceModel() ).
4. Create a stand-alone Legato component that requires the le_info API:
api_client/Component.cdef
requires:
{
api:
{
le_info.api
}
}
5. Build the component using the mkcomp stand-alone option:
$ mkcomp --stand-alone -t wp7 -i $LEGATO_ROOT/interfaces/modemServices api_client
@c 6. Compile and link your executable with the header files and library generated by mkcomp:
@code
$ export WP7_CC=/opt/swi/y16-ext/sysroots/x86_64-pokysdk-linux/usr/bin/arm-poky-linux-gnueabi/arm-poky-linux-gnueabi-gcc
$ $WP7_CC -c main.c -I_build -I$LEGATO_ROOT/framework/c/inc
$ $WP7_CC -o legacyProgram main.o libIF_le_info_client.so -L$LEGATO_ROOT/build/wp7/bin/lib -llegato
7. Bundle the additional library generated by mkcomp into your .adef file:
bundles:
{
file:
{
[x] legacyProgram /bin/
[r] libIF_le_info_client.so /lib/
}
}
8. Specify which instance of the le_info service your app should use by creating a binding in the .adef file:
bindings:
{
.le_info -> modemService.le_info
}
9. Re-generate your application bundle and install it on target:
$ mkapp -t wp7 legacyProgram.adef
$ instapp legacyProgram.wp7 192.168.1.2
Installing application 'legacyProgram' from file 'legacyProgram.wp7'.
Removing app 'legacyProgram'...
Deleted user 'applegacyProgram'.
Installing app 'legacyProgram'...
Created user 'applegacyProgram' (uid 1011, gid 1011).
DONE
$
Add more APIs
Adding subsequent APIs is even simpler.
1. Add the API to the list required by your stand-alone component:
api_client/Component.cdef
requires:
{
api:
{
le_info.api
le_data.api
}
}
2. Build the component using mkcomp –stand-alone:
$ mkcomp --stand-alone -t wp7 -i $LEGATO_ROOT/interfaces/modemServices -i $LEGATO_ROOT/interfaces/dataConnectionService api_client
3. Compile and link your executable with the header files and library generated by mkcomp:
$ export WP7_CC=/opt/swi/y16-ext/sysroots/x86_64-pokysdk-linux/usr/bin/arm-poky-linux-gnueabi/arm-poky-linux-gnueabi-gcc
$ $WP7_CC -c main.c -I_build -I$LEGATO_ROOT/framework/c/inc
$ $WP7_CC -o legacyProgram main.o libIF_le_info_client.so libIF_le_data_client.so -L$LEGATO_ROOT/build/wp7/bin/lib -llegato
4. Bundle the additional library generated by mkcomp into your .adef file:
bundles:
{
file:
{
[x] legacyProgram /bin/
[r] libIF_le_info_client.so /lib/
[r] libIF_le_data_client.so /lib/
}
}
5. Specify which instance of the service your app should use by creating a binding in the .adef file:
bindings:
{
.le_info -> modemService.le_info
.le_data -> dataConnectionService.le_data }
6. Re-generate your app bundle and install it on the target:
$ mkapp -t wp7 legacyProgram.adef
$ instapp legacyProgram.wp7 192.168.1.2
Installing application 'legacyProgram' from file 'legacyProgram.wp7'.
Removing app 'legacyProgram'...
Deleted user 'applegacyProgram'.
Installing app 'legacyProgram'...
Created user 'applegacyProgram' (uid 1011, gid 1011).
DONE
$
Handlers
If you need asynchronous callbacks (i.e., handlers), use le_event_GetFd() and le_event_ServiceLoop().
See Integrating with Legacy POSIX Code for details.
Here's some sample code:
struct pollfd pollControl;
pollControl.events = POLLIN;
while (true)
{
int result = poll(&pollControl, 1, -1);
if (result > 0)
{
{
}
}
else
{
LE_FATAL(
"poll() failed with errno %m.");
}
}
Sample legacy app
Sample Legacy C apps are available in the Legato/apps/sample/legacy directory.
Copyright (C) Sierra Wireless Inc. Use of this work is subject to license.