24
nesC: nesC: A Programming A Programming Language Language for Motes for Motes David Gay, Phil Levis, Eric David Gay, Phil Levis, Eric Brewer, Rob von Behren, Brewer, Rob von Behren, Nikita Borisov, Mike Chen, Nikita Borisov, Mike Chen, David Culler David Culler Intel Research, UC Berkeley Intel Research, UC Berkeley

NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Embed Size (px)

Citation preview

Page 1: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

nesC:nesC:A Programming A Programming

LanguageLanguagefor Motesfor Motes

David Gay, Phil Levis, Eric David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Brewer, Rob von Behren, Nikita

Borisov, Mike Chen, David CullerBorisov, Mike Chen, David CullerIntel Research, UC BerkeleyIntel Research, UC Berkeley

Page 2: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

The State of the MotesThe State of the Motes

TinyOS programs hard to writeTinyOS programs hard to write No compiler:No compiler:

verbose, unwieldy syntaxverbose, unwieldy syntax many compile-time checks missingmany compile-time checks missing

No support for common idioms:No support for common idioms: state-machine-like programsstate-machine-like programs split-phase operationssplit-phase operations atomicity guarantees, etcatomicity guarantees, etc

Page 3: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

A Long-term SolutionA Long-term Solution

We are working on an improved languageWe are working on an improved language Component-basedComponent-based Better support for common idiomsBetter support for common idioms

split-phase ops, state-machines, etcsplit-phase ops, state-machines, etc Clean atomicity modelClean atomicity model

Very much in the design/investigation Very much in the design/investigation stagestage

Page 4: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

A Short-term Solution: A Short-term Solution: nesCnesC

A cleaned up language for TinyOSA cleaned up language for TinyOS Goals:Goals:

Easier to useEasier to use Allow whole-program optimisationsAllow whole-program optimisations Base for language experimentationBase for language experimentation

Pronounced “nestlé”Pronounced “nestlé”

Page 5: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

nesC: Easier to UsenesC: Easier to Use

Nicer syntaxNicer syntax Check errorsCheck errors

Missing connectionsMissing connections Type errors in connectionsType errors in connections Cycles, incorrect directionsCycles, incorrect directions

Interfaces:Interfaces: Group related functionality (caller, callee):Group related functionality (caller, callee):

sendMsg: sendMsg: users: call send(m), implement sendDone(m)users: call send(m), implement sendDone(m) implementer: implement send(m), call sendDone(m)implementer: implement send(m), call sendDone(m)

Concise wiringConcise wiring

Page 6: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

The Old ModelThe Old Model

ComponentsComponents .comp.comp: :

specificationspecification .C.C: behaviour: behaviour .desc.desc: select and : select and

wirewire specification:specification:

accepts accepts commandscommands

uses uses commandscommands signals signals eventsevents handles handles eventsevents

comp1:C code

comp3

comp4comp2:.desc

application:.desc

Page 7: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

The Old Model, The Old Model, continuedcontinued

4 kinds of components:4 kinds of components: .desc only (ex: cnt_to_leds): .desc only (ex: cnt_to_leds):

top-level components and wiring for an applicationtop-level components and wiring for an application .C and .comp (ex: CLOCK): .C and .comp (ex: CLOCK):

a component implemented in Ca component implemented in C .desc and .comp (ex: GENERIC_COMM): .desc and .comp (ex: GENERIC_COMM):

a component implemented by connecting other a component implemented by connecting other componentscomponents

.C, .comp and .desc (ex: INT_TO_RFM):.C, .comp and .desc (ex: INT_TO_RFM): a component implemented in C with predefined wiring a component implemented in C with predefined wiring

to other componentsto other components

Page 8: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

The nesC ModelThe nesC Model

Components: 1 Components: 1 filefile specificationspecification implementationimplementation

modulemodule: C : C behaviourbehaviour

configurationconfiguration::select and wireselect and wire

specificationspecification providesprovides

interfaceinterface requiresrequires interface interfaceapplication:

configuration

comp1:module

comp3

comp4comp2:configuration

Page 9: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

The nesC Model, The nesC Model, continuedcontinued

2 kinds of components2 kinds of components module: module: waswas .C and .comp .C and .comp configuration: configuration: waswas .desc and .comp .desc and .comp

What happened to the other 2 kinds of What happened to the other 2 kinds of components ?components ? .desc only (ex: cnt_to_leds): .desc only (ex: cnt_to_leds):

use a configuration with empty specification { }use a configuration with empty specification { } .C, .comp and .desc (ex: INT_TO_RFM):.C, .comp and .desc (ex: INT_TO_RFM):

use a configuration and module (2 files)use a configuration and module (2 files) naming convention: IntToRfm (configuration), IntToRfmM naming convention: IntToRfm (configuration), IntToRfmM

(module)(module) allows module to be re-used with different wiringallows module to be re-used with different wiring

Page 10: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

InterfacesInterfaces Group related functionality, e.g.:Group related functionality, e.g.:

split-phase operation (send, sendDone)split-phase operation (send, sendDone) standard control interface: init, powerstandard control interface: init, power

Specifies bi-directional calls (Specifies bi-directional calls (definesdefines, , usesuses):):interface SendMsg { interface SendMsg {

definesdefines command result_t send(uint16_t to, TOS_MsgPtr msg); command result_t send(uint16_t to, TOS_MsgPtr msg);

usesuses event result_t sendDone(TOS_MsgPtr msg, result_t ok); event result_t sendDone(TOS_MsgPtr msg, result_t ok);

}}

if component C with interface I has if component C with interface I has function f:function f: if I is required and f is if I is required and f is usesuses, C must define f, C must define f if I is provided and f is if I is provided and f is definesdefines, C must define f, C must define f

Page 11: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Some InterfacesSome Interfacesinterface Leds {interface Leds {

defines {defines {

command result_t init();command result_t init();

command result_t redOn();command result_t redOn();

command result_t redOff();command result_t redOff();

command result_t redToggle();command result_t redToggle();

......

}}

}}

interface Clock { defines command result_t setRate(char interval, char scale); uses event result_t fire();}

interface StdControl { defines { command result_t init(); command result_t power(char mode); }}

Page 12: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Some More InterfacesSome More Interfaces

interface SendMsg { defines command result_t send(uint16_t to, TOS_MsgPtr msg); uses event result_t sendDone(TOS_MsgPtr msg, result_t ok);}

interface ReceiveMsg { uses event TOS_MsgPtr receive(TOS_MsgPtr m);}

interface ADC { defines command result_t getData(); defines command result_t getContinuousData(); uses event result_t dataReady(uint16_t data);}

But where did the Active Message type go ?But where did the Active Message type go ? But where did the ADC port go ?But where did the ADC port go ?

Page 13: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Parameterised InterfacesParameterised Interfaces Specify a numeric parameter for an interface in a Specify a numeric parameter for an interface in a

component:component: argument value specified in configurationsargument value specified in configurations dynamic dispatch (receive, sendDone), implicit argument (send)dynamic dispatch (receive, sendDone), implicit argument (send) Like the current scheme for receiving active messagesLike the current scheme for receiving active messages

Used also for ADC ports, exclusive EEPROM accessUsed also for ADC ports, exclusive EEPROM access

configuration MyApp ... implementation {configuration MyApp ... implementation { uses MyMain, GenericComm;uses MyMain, GenericComm; MyMain.Msg1 -> GenericComm.Send[12];MyMain.Msg1 -> GenericComm.Send[12]; MyMain.Msg2 -> GenericComm.Receive[99];MyMain.Msg2 -> GenericComm.Receive[99];}}

module MyMain {module MyMain { requires interface Send Msg1;requires interface Send Msg1; requires interface Receive Msg2;requires interface Receive Msg2;}}implementation {implementation { event Msg2.receive(MsgPtr m) {event Msg2.receive(MsgPtr m) { call Msg1.send(myMsg);call Msg1.send(myMsg); }}}}

interface Receive {interface Receive { uses event receive(MsgPtr m);uses event receive(MsgPtr m);}}interface Send {interface Send { defines command send(MsgPtr m);defines command send(MsgPtr m); uses event sendDone(MsgPtr m);uses event sendDone(MsgPtr m);}}

configuration GenericComm {configuration GenericComm { provides interface Send[char id];provides interface Send[char id]; provides interface Receive[char id];provides interface Receive[char id];} } implementation { ... }implementation { ... }

Page 14: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Miscellaneous FeaturesMiscellaneous Features

defaultdefault events and commands (cf: _NULL_FUNC) events and commands (cf: _NULL_FUNC) some commands, events not always connectedsome commands, events not always connected specify default behaviour in the absence of connection, specify default behaviour in the absence of connection,

e.g.:e.g.: defaultdefault event TOS_MsgPtr receive(TOS_MsgPtr msg) event TOS_MsgPtr receive(TOS_MsgPtr msg)

{ return msg; } { return msg; }

includesincludes is used to include C types/constants/etc is used to include C types/constants/etc for use in an interface or componentfor use in an interface or component these types are accessible to all components that use these types are accessible to all components that use

the interface or componentthe interface or component use, e.g., to share packet format specification across use, e.g., to share packet format specification across

componentscomponents nesC source code is nesC source code is notnot preprocessed preprocessed

Page 15: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

ImplementationImplementation nesc1 takes a “closed” component (no interfaces) nesc1 takes a “closed” component (no interfaces)

and:and: Checks nesC errorsChecks nesC errors

Unknown/multiply-defined interfaces, components, etcUnknown/multiply-defined interfaces, components, etc Connections (missing, cyclical, type-incorrect, wrong direction)Connections (missing, cyclical, type-incorrect, wrong direction)

Checks (most) C errorsChecks (most) C errors Generates one C-file for the applicationGenerates one C-file for the application

Includes only reachable code (prunes out unreachable Includes only reachable code (prunes out unreachable functions)functions)

Generated in reverse-topological-call-orderGenerated in reverse-topological-call-order Allows gcc’s inliner to do a much better inlining jobAllows gcc’s inliner to do a much better inlining job

avr-gcc compiles nesc1 outputavr-gcc compiles nesc1 output Generated code has #line directives, so clean error Generated code has #line directives, so clean error

messagesmessages

Page 16: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

StatusStatus

Compiler complete (some bugs expected)Compiler complete (some bugs expected) Basic infrastructure and components for Basic infrastructure and components for

MicaMica (old) radio stack(old) radio stack ADC, Clock, Leds, EEPROM, serial portADC, Clock, Leds, EEPROM, serial port

Apps ported: Apps ported: Blink, CntTo{Leds,Rfm,LedsAndRfm}, Blink, CntTo{Leds,Rfm,LedsAndRfm},

RfmToLedsRfmToLeds SenseToLeds, Chirp, Oscilloscope, EEPROMTestSenseToLeds, Chirp, Oscilloscope, EEPROMTest GenericBaseGenericBase

Page 17: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Status: Code SizeStatus: Code Size

ApplicationApplication C C (TinyOS)(TinyOS)

nesCnesC SavingsSavings

BlinkBlink 10921092 796796 27%27%

CntToLedsCntToLeds 11701170 972972 17%17%

SenseToLedsSenseToLeds 16361636 10861086 34%34%

OscilloscopeOscilloscope 27922792 22302230 20%20%

RfmToLedsRfmToLeds 52265226 41684168 20%20%

GenericBaseGenericBase 45444544 46324632 -2%-2%

CntToRfmCntToRfm 52205220 46784678 10%10%

CntToLedsAndCntToLedsAndRfmRfm

55445544 48504850 13%13%

ChirpChirp 55165516 49484948 10%10%

EEPROMTestEEPROMTest 78307830 62206220 21%21%

Page 18: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

PlansPlans

Goal: Switch all TinyOS C code to nesCGoal: Switch all TinyOS C code to nesC Stage 1: convert all “standard” components & appsStage 1: convert all “standard” components & apps

Who: The TinyOS teamWho: The TinyOS team Support: Mica, Rene2, all sensor boardsSupport: Mica, Rene2, all sensor boards

Stage 1a: Phil Levis will “port” TOSSIM to nesCStage 1a: Phil Levis will “port” TOSSIM to nesC Stage 1b: Eric Brewer will write porting guide, Stage 1b: Eric Brewer will write porting guide,

nesC tutorialnesC tutorial Stage 2: distribute nesC in next TinyOS releaseStage 2: distribute nesC in next TinyOS release Stage 3: discontinue support for macros/perl scriptsStage 3: discontinue support for macros/perl scripts

Goal: Improve nesCGoal: Improve nesC See Eric’s talkSee Eric’s talk

Page 19: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Open IssuesOpen Issues

Naming Convention (Java-inspired)Naming Convention (Java-inspired) Interface designInterface design Revisit some component designsRevisit some component designs Directory structureDirectory structure

Page 20: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

ConclusionsConclusions

nesC much nicer to use than TinyOSnesC much nicer to use than TinyOS No more obscure C compiler warnings/errorsNo more obscure C compiler warnings/errors No more obscure bugs due to typosNo more obscure bugs due to typos No more obscure infinite loops due to wiring No more obscure infinite loops due to wiring

restrictionsrestrictions nesC produces smaller code than TinyOSnesC produces smaller code than TinyOS

Prunes unreachable codePrunes unreachable code Inlining across component boundariesInlining across component boundaries

The best is yet to come!The best is yet to come! Short-term: multiple instantiation, better inlining Short-term: multiple instantiation, better inlining

selection, packet format specificationselection, packet format specification Long-term: language improvements for bug Long-term: language improvements for bug

preventionprevention

Page 21: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

Packet Format Packet Format SpecificationSpecification

Write a C file with the packet type: Write a C file with the packet type: // IntMsg.th: The message type for IntToRfm/RfmToInt// IntMsg.th: The message type for IntToRfm/RfmToInttypedef struct {typedef struct { char val;char val; int src;int src;} IntMsg;} IntMsg;

enum {enum { AM_INTMSG = 4AM_INTMSG = 4};};

Use it in nesC components via Use it in nesC components via includesincludes Automatic generation of corresponding Automatic generation of corresponding

Java type and marshaller/unmarshallerJava type and marshaller/unmarshaller

Page 22: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

ComponentsComponents

componentscomponentsmodule module C1C1 { {

requires interface triangle;requires interface triangle;

} implementation { ... }} implementation { ... }

module module C2C2 { {

provides interface triangle in;provides interface triangle in;

requires {requires {

interface triangle out;interface triangle out;

interface rectangle side; }interface rectangle side; }

} implementation { ... }} implementation { ... }

configuration configuration C3C3 { {

provides interface triangle;provides interface triangle;

provides interface rectangle;provides interface rectangle;

} implementation { ... }} implementation { ... }

C1

C2

C3

Page 23: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

ConfigurationsConfigurations Connect componentsConnect components

configuration app { }configuration app { }implementation {implementation {

uses uses c1c1, , c2c2, , c3c3;;c1 -> c2; // implicit interface sel.c1 -> c2; // implicit interface sel.c2.out -> c3.triangle;c2.out -> c3.triangle;c3 <- c2.side;c3 <- c2.side;

}}

Partial configurations:Partial configurations:component c2c3 {component c2c3 { provides interface triangle t1;provides interface triangle t1;}}implementation {implementation { uses uses c2c2, , c3c3;;

t1 -> c2.in;t1 -> c2.in;c2.out -> c3.triangle;c2.out -> c3.triangle;c3 <- c2.side;c3 <- c2.side;

}}

C1

C2

C3

C2

C3

Page 24: NesC: A Programming Language for Motes David Gay, Phil Levis, Eric Brewer, Rob von Behren, Nikita Borisov, Mike Chen, David Culler Intel Research, UC Berkeley

ModulesModules ““C” implementation of C” implementation of

componentscomponents all top-level all top-level

declarations private, declarations private, except those specified except those specified in the components in the components interfaceinterface

module C2 { module C2 { provides interface send in;provides interface send in; requires interface send out;requires interface send out;} implementation {} implementation { enum { ready, busy } state;enum { ready, busy } state;

command in.send(Message m) command in.send(Message m) {{

if (state == busy) return 0;if (state == busy) return 0; state = busy;state = busy; call out.send(m);call out.send(m); return 1;return 1; }}

event out.send_done(Message event out.send_done(Message m) {m) {

state = ready;state = ready; signal in.send_done(m);signal in.send_done(m); }} ......}}