Programdesign (Sun SPOT)
Denne artikel indeholder informationer omkring den konkrete udformning af Sun SPOT programmet. Designet ligger tæt op ad kravspecifikationen
Generelt
Vi vil som altid i forbindelse med grafisk brugerflade programmering benytte os af model-view-control design mønstret.
Model
Modellen er den del af systemet, som skal håndtere alle data, hvilket inkluderer positionsbestemmelse samt protokol. Disse punkter bliver behandlet selvstændigt nedenfor.
Modellen kommunikerer med den grafiske brugerflade igennem interfaces. Brugerfladen må ikke i sig selv indeholde vigtige oplysninger såsom variabler, sensor lister osv. Disse gemmes og vedligeholdes i modellen.
Protokol
Protokollen opdeles som i kravspecifikationen i to dele. En for basisstationen og en for de frie sensorer.
Grundlæggende dataudveksling og -manipulering
I vores tidligere Sun SPOT projekter, har vi savnet bedre muligheder for at manipulere med vores frie sensorer i runtime. Tidligere har vi været nød til at overføre en ny version af programmet til sensoren hver gang en ændring skulle foretages. Dette er meget tidskrævende, hvis man f.eks. sidder i en debugging situation. Til dette projekt forestiller vi os en løsning, som giver mulighed for både at læse og skrive en sensors variabler samt kalde bestemte metoder direkte fra basisstationen i runtime. Dette vil gøre hele systemet mere fleksibelt, da vi derved lettere kan teste og debugge samt eksperimentere med sensoreren uden at skulle overføre nye programmer hele tiden.
Løsningen bygges op omkring datagram pakker!
Variabler
Vi er nød til at håndtere variablerne på sensoren anderledes end normalt. Helt konkret skal alle de variabler som basisstationen skal kunne manipulere med være objekter, der organiseres i en Hashtable. Nøglerne i denne Hashtable er variabelnavnene og til hver nøgle knytter sig et objekt som repræsentere variablens værdi. Basisstationen kan få tilsendt en enkelt variabel eller en hel liste med variabelnavne i en pakke, hvis de f.eks. skal vises i en grafisk brugergrænseflade.
Metoder
For at give basisstationen mulighed for at kalde en sensors metoder, skal følgende overvejelser gøres:
- Må en metode kunne returnere en værdi/objekt?
- Dette kan muligvis godt lave sig gøre, så længe den værdi der returneres er en primitiv datatype (int, long, double, string, boolean mm.). Når metoden returere sin værdi, skal den dermed sendes i en pakke tilbage til basisstationen.
- Må en metode tage argumenter?
- Ja, når basisstationen sender en pakke med et metodekald til sensoren, skal pakken indeholde de argumenter som metoden kræver. Basisstationen ved ikke hvilke argumenter en bestemt metode kræver, det brugeren/programmøren vide!
Basisstation
Basisstationenen skal kunne holde styr på mange ting på en gang. Det er derfor nødvendigt at benytte trådet programmering.
Opgaver (ukomplet liste):
- Håndtering af indkomne datapakker.
- Data. Protokollen giver mulighed for at sende variabelværdier til og fra sensorene. Datapakker håndteres konkret et andet sted.
- Ping. Hver frie sensor skal med passende interval gøre opmærksom på sin tilstedeværelse til basisstationen og nabosensorer.
- Kommunikations vedligeholdelseskommandoer, herunder:
- Hver frie sensor vil forsøge at oprette forbindelse til basisstationen. Der er således et konstant behov for, at sensorer kan kontakte basisstationen.
- Hvis en sensor pludselig mister forbindelse til en anden sensor, skal dette rapporteres. Konkret "opdages" en mistet forbindelse ved at en ping pakke udebliver i længere tid end normalt.
- Basisstationen skal kende alle sensorer i netværket. Derfor skal alle frie sensorer sende en liste over nabosensorer, så basisstationen på den måde kan blive bekendt med eventuelle sensorer, som ligger uden for dens rækkevidde.
- Håndtering af data.
- Som beskrevet i kravspecifikationen skal det være muligt til hver en tid at se en sensors målinger. Vi ved endnu ikke, om disse målinger skal gemmes eller blot være den seneste måling.
Herudover har brugeren af systemet en række funktioner til rådighed gennem gui'en:
Pseudokode
Dette punkt vil løbende blive opdateret eftersom protokollen udvikler sig.
Fri sensor (Sun SPOT)
De frie sensorer er primært kommunikationled i en kæde/rute, som forbinder hele sensornetværket. Kravspecifikationen beskriver, hvad de frie sensorer skal kunne, hvilket uddybes her. Der er ligesom for basisstationen behov for at benytte trådet programmering.
Hver af de følgende opgaver håndteres af en enkelt tråd:
- Oprettelse af forbindelse og efterfølgende pings til både nabosensorer og basisstation.
- Modtagelse og distribuering af indkommende opgaver samt forespørgsler.
- Opgavehåndtering, herunder:
- Videresendelse af beskeder.
- Besvarelse på forespørgsler.
Opgave/forespørgelsprotokol
Overvejelse: Skal en sensor kunne sende en slags fejlmeddelser til basisstationen? F.eks. hvis der sendes ugyldig argumenter til et metodekald
package = data_to_base {name type value}+ | request_from_base address request_line | broadcast request_line = "get" get_type | "set" name value | "run" name {arguments}* get_type = name | "variables" | "functions" | "neighbours" name = alpha{alpha | number}* value = rnumber | alpha+ | bool address = "0014.4F01." subaddr "." subaddr subaddr = hex{4} data_to_base = 1 request_from_base = 2 broadcast = 3 type = byte | int | long | float | double | char | string | boolean byte = 0 int = 1 long = 2 float = 3 double = 4 char = 5 string = 6 boolean = 7
"hex" betegner et hexadecimal tal. Altså 0 til F. "alpha" betegner bogstaver fra a-z og A-Z. "number" er et positivt heltal bestående af cifrene 0-9. "rnumber" er et rationelt tal. "bool" en sandhedsværdi, som kan være enten true eller false.
Pseudokode
Dette punkt vil løbende blive opdateret eftersom protokollen udvikler sig.
Tråd 1: Oprettelse af forbindelse og efterfølgende pings
while (true) { while (!connected) { broadcast(this.id); pause(random long); // milisecs } while (connected) { sendToBaseStation(ping & sensordata); pause(10000); // milisecs } }
Tråd 2: Modtagelse af opgaver samt distribuering:
while (true) { while (connected) { receive(request); distributeRequest(request); // Tilføj til en kø eller lignende pause(100); } pause(5000); }
Tråd 3: Opgavehåndtering
while (true) { while (!requestQueue.isEmpty) { handleRequest(requestQueue.poll); // Videresend besked pause(100); } pause(1000); }
Positionsbestemmelse
Model design
Ovenstående beskrivelser giver anledning til følgende programopbygning for modellen.