SE4Binome2024-7

De projets-se.plil.fr
Aller à la navigation Aller à la recherche

Code Source et autre programmes

TESTS PRELIMINAIRES

Vérification des connecteurs HE-10

Nous avons testé un 7-segments sur tous les connecteurs HE-10. Vous pouvez le voir dans la sous-section COMMUNICATION SPI de la section ORDONNANCEUR.

Lecture Carte SD

Cette image montre la detection de la carte SD sur le Shield par l'ordinateur. On peut observer son type ou sa taille et d'autres informations.

CarteSD.png

Fonctionnement des LEDs

Avant de nous aventurer dans les méandres de l'ordonnanceur, nous devons vérifier que toutes les LEDs sont bien connectées. Nous n'avons pas de photos du dit test mais nous vous invitons à aller voir la sous-section CLIGNOTEMENT DES LEDs dans la section ORDONNANCEUR. Vous pouvez même observer une différence de fréquence entre les clignotements.

ORDONNANCEUR

SQUELETTE BASIQUE DE L'ORDONNANCEUR

Le but de l'ordonnanceur est de répartir l'éxecution des multiples tâches que doit exécuter l'arduino, et que celles-ci nous semblent simultanées. Pour faire cela, à intervalle régulier (puisque nous fonctionnons en Round Robin),l'Interrupt Service Routine (ISR) va sauvegarder l'état des registres, interrompre la tâche en cours, puis appeler l'ordonnanceur qui va choisir quelle tâche doit maintenant s'exécuter, puis restaurer l'état des registres.

Pour réaliser l'ordonnanceur, nous commençons par initialiser un minuteur qui va définir la fréquence d'interruption (diviseur), le mode de la minuterie (CTC1)) et la période (periode)).

Ensuite, nous définissons le comportement qu'il va adopter à chaque interruption. Cela est géré par la fonction ISR en mode NAKED, ce qui implique que l'on va devoir gérer les sauvegardes

des registres nous mêmes (lors d'une interruption, nous commençons toujours par sauvegarder l'état des registres et les restaurons à la fin, sans quoi nous perdons tout le contexte la précédant).

Nous définissons donc en parallèle deux macros SAVE_REGISTERS() et RESTORE_REGISTERS() que nous appelons respectivement au début et à la fin de chaque interruption.

Puis nous créons notre fonction ordonnanceur, qui est pour l'instant vide, puisque les tâches n'ont pas encore été construites, et c'est ce à quoi nous allons maintenant nous atteler.

STRUCTURE DES TÂCHES

La structure des tâches est la suivante :

typedef struct Task {
   void (*fonction)(void);    // Pointeur vers une fonction prenant aucun paramètre et ne retournant rien
   uint16_t SPointer;         // Pointeur de pile
   int state;                 // État de la tâche
   struct prog_data data;     // Données de la tâche
} Task;

struct prog_data {
   int Type;
   union {
       int delay;  // On peut ajouter d'autres types de données ici si nécessaire
   } data;
};

Nous avons un pointeur destiné à pointer vers la fonction à exécuter pour cette tâche. Le pointeur SPointer sert à sauvegarder la position du pointeur de pile pour cette fonction à l'interruption, chaque fonction ayant sa propre pile d'exécution. Cela est vital car lorsque l'on voudra continuer l'exécution de cette fonction par la suite, nous devons savoir l'état dans lequel elle s'était arrêtée. L'état permet d'intégrer une fonction sleep par la suite, qui rendra la tâche inactive pendant le delai delay contenu dans data.

Les tâches à éxecuter seront toutes regroupées dans une liste de tâches Task TaskList[NB_TASKS] dans l'ordonnanceur.

Finalement, nous ajoutons cette ligne :

currentTask = (currentTask + 1) % NB_TASKS;

dans l'ordonnanceur, ce qui permet de passer d'une tâche à la suivante à chaque interruption.

CLIGNOTEMENT DES LEDs

Nous avons utilisé cette structure pour créer deux tâches de clignotement de LEDs, task_led1 et task_led2, dans ordonnanceur1.c à des fréquences premières entre elles. Vous trouverez ci-dessous une vidéo du résultat. Cependant, il y a un léger problème concernant la manière dont ces tâches sont programmées : nous utilisons la fonction _delay_ms de la bibliothèque delay.h, plutôt que d'endormir la tâche. Cela signifie que la tâche est quand même exécutée et ne fait qu'attendre pendant son temps d'exécution. Plutôt que de faire ça, on va créer une fonction delay, qui va endormir la tâche pendant le temps désiré et qui permettra de libérer ce temps de travail inutile pour plutôt exécuter d'autres tâches à la place.


FONCTION DELAY

Pour cette fonction delay, nous changeons l'état de la tâche à endormir en SLEEPING, puis assignons la valeur time donnée en paramètre au delay de la tâche. Nous remettons le compteur à 0 et appelons l'ISR pour être sûr que le delay soit le bon(la fonction delay s'éxecute pendant une éxecution de tâche, on verra juste après pourquoi cela risque de fausser le delay).

void delay(int time)
{
  TaskList[currentTask].state = SLEEPING;
  TaskList[currentTask].data.data.delay = time;
  TCNT1 = 0;
  TIMER1_COMPA_vect();
}

Ensuite, nous allons changer l'ordonnanceur pour qu'il puisse gérer l'état SLEEPING.

  • Si la currentTask est en mode SLEEPING:
    • Si son delay est positif, nous soustrayons une durée elapsed_time fixe correspondant à une période d'éxecution au delay de cette tâche. C'est ici qu'on voit l'intérêt de reset le timer et d'appeler l'ISR : puisque elapsed_time est fixe et indépendant du timer TCNT1, il ne prend pas en compte le temps auquel s'est éxecuté le delay (le timer n'était pas à un multiple fixe de la période).
    • Si son delay est négatif ou nul, nous restaurons l'état de tâche à ACTIVE.

Puis, dans la sélection de tâche à éxecuter ensuite, nous testons si l'état de la tâche est SLEEPING. Si c'est le cas, nous regardons la suivante, jusqu'à tomber sur une tâche en mode ACTIVE, que l'on va alors éxecuter.

COMMUNICATION SERIE

Maintenant que tout est fonctionnel, nous nous attaquons à la communication série. Toutes les fonctions sont disponibles dans comm_serie.c. Nous commençons par initialiser la communication en définissant la vitesse, configurons le mode (envoi et réception), puis programmons deux fonctions serie_recevoir et serie_envoyer ayant un nom peu équivoque. Le but est pour l'instant d'échanger via minicom, nous tapons des caractères au clavier qui seront renvoyés par l'arduino dans le terminal.

Dans serie_envoyer, nous vérifions si nous avons reçu un caractère. Si c'est le cas, nous écrivons la data reçue sur UDR0 correspondant au port série. Puis, la fonction donne la valeur 0 a is_data_received (variable globale), signifiant qu'il n'y a plus de data à envoyer, et remettons data a une valeur nulle.

Dans serie_recevoir, nous attendons qu'une valeur soit écrite sur UDR0 puis assignons cette valeur à data, et passons is_data_received à 1, signifiant que nous avons reçu une data qu'il faut envoyer.

Finalement, nous intégrons ces deux fonctions dans des tâches que nous ajoutons à note liste de tâches à éxecuter. Vous pouvez trouver ci-dessous le résultat.

Plus simplement, lorsqu'on écrit un caractère sur le clavier de l'ordinateur, ce dernier est transmis à l'Arduino via la connexion USB. Dès que l'Arduino reçoit ce caractère, la variable is_data_received passe à 1 grâce à la fonction serie_recevoir. Ensuite, l'Arduino renvoie ce même caractère au terminal (Minicom) en utilisant la fonction serie_envoyer. Ainsi, on peut voir ce caractère affiché sur le terminal, ce qui confirme que la communication série fonctionne correctement.

COMMUNICATION SPI

Après la communication série, passons à la SPI. Par manque d'originalité, toutes les fonctions sont regroupées dans comm_spi.c.

Notre but est de communiquer avec un afficheur 7 segments. Celui utilisé accepte des messages de 4x8octets, avec chaque octet correspondant à un des chiffres affichés sur le 7 Segment. Il y a également des commandes spéciales pour réinitialiser l'affichage.

Nous commençons par initialiser la communication. Pour cela, nous avons au préalable défini des macros conçernant nos PIN de MISO, MOSI, et les pins reliés à un connecteur HE-10, (qui dépendent de comment à été routé le shield). Nous les utilisons dans une fonction spi_init, qui va définir les entrées et sorties, et activer la communication spi en mode maître sur l'arduino.

Nous avons des fonctions  spi_select et spi_deselect qui (dé)sélectionnent le pin slave sur lequel communiquer.

A chaque message ou commande spéciale à envoyer, nous devrons faire appel à spi_activer et spi_desactiver avant et après respectivement, pour (dés)activer le périphérique.

La fonction spi_echange envoie un octet sur le port SPI, correspondant à output qui est en paramètre.

Finalement nous avons spi_clearDisplay qui réinitialise l'affichage à l'aide de la commande 0x76, et spi_setLight qui configure la luminosité de l'afficheur.

Pour afficher des caractères nous devons donc activer le périphérique puis envoyer 4 fois un octet à l'aide de spi_échange, et désactiver le périphérique.

Vous trouverez ci-dessous une photo de l'afficheur en fonctionnement, puis une vidéo montrant l'éxecution de la tâche associée à la fonction sevenseg, disponible dans ordonnanceur1.c

7SegmentPicture.jpg

Problèmes rencontrés avec la COMMUNICATION SPI

Lors de la programmation de notre carte RNDIS, nous avons rencontré un problème de communication SPI de notre carte RNDIS vers notre Shield. Nous pouvons envoyer des paquets/données du Shield vers la carte RNDIS mais pas dans l'autre sens. Le problème résidait sur le Shield. Plus particulièrement sur le releveur de niveau de tension. La résistance soudée à la sortie du PIN MOSI_1 ne devrait pas être ici. Dû à cette erreur de design, le releveur de niveau faisait l'inverse de ce qu'il doit normalement faire : il baissait notre niveau de tension. Normalement, le releveur de niveau doit augmenter la tension pour quelle puisse être utilisée/utilisable par le MicroP. Lors de nos tests sur oscilloscope, nous avions +5V du Shield vers notre carte RNDIS, ce qui est la tension optimale mais n'obtenons que +1.5V de notre carte RNDIS vers notre Shield ce qui est bien insuffisant car les MicroP que nous avons ne fonctionne qu'avec des tensions à minima de +3.3V. Nous avons d'abord tenter de couper la piste à l'entrée du PIN MISO et d'y mettre la résistance qui est en sortie du PIN MISO_1 et de remplacer la résistance en sortie du PIN MISO_1 par un fil. Cela régla notre problème de tension mais nous ne pouvions plus détecter la carte SD. Nous avons donc enlevé toutes les résistances et fils des pistes MOSI à l'entrée et sortie du releveur de niveau et avons court-circuité les deux pistes. Il faut aussi sectionner le fil de cuivre MOSI sinon le courant ira sur le fil de cuivre MISO_1 ET le fil MOSI et nous voulons que le courant aille uniquement sur MISO_1 . Cela régla notre problème de tension ET de détection de carte SD.

Schéma montrant les tests que nous avons fait pour régler le problème de tension du MISO
Schéma montrant comment nous avons pu régler le problème de tension en MISO et de détection de la carte SD
Schéma montrant comment nous avons pu régler le problème de tension en MISO et de détection de la carte SD

Programmation de la carte RNDIS

Pour utiliser la carte RNDIS, nous allons créer notre protocole Ethernet en s'inspirant de l'ARP. Cela permettra de ne traiter que les paquets associés au projet, et de donner une structure adaptée à nos besoins. Pour rappel, le but est d'envoyer des paquets de la carte réseau chaque fois que la carte mère envoie une commande à la carte réseau. La commande contiendra éventuellement des données supplémentaires (si la commande est un ls, il faut préciser le chemin du dossier dans lequel l'éxecuter) qui seront traitées par le PC dans un programme qui tournera en continu. Ce programme réceptionne les paquets, les interprète et envoie les réponses à la carte RNDIS. Puis la carte RNDIS décode le paquet réponse, et envoie les données par SPI à la carte mère.

Pour résumer, la carte RNDIS a 4 tâches principales :

  • Recevoir les commandes SPI envoyées par la carte mère
  • Interpréter ces commandes et former puis envoyer les paquets correspondants
  • Recevoir les réponses envoyées par le PC
  • Envoyer les données contenu dans les réponses par SPI à la carte mère

Test avec protocole connu

Tout d'abord, nous allons vérifier que la carte fonctionne avec un protocole connu. Nous allons donc utiliser l'exemple de carte RNDIS fourni dans la LUFA donnée au semestre précédent.

En uploadant la LUFA, on voit bien après un lsusb que le périphérique apparaît dans la liste :

Ipa apres configuration ip.png


Nous allons tester le fonctionnement de la carte avec un ping. Nous devons donc ajouter des addresses IP associées à l'interface de la carte. On efffectue la commande ip address add 10.0.0.100/24, on up l'interface avec ip link set usb0 up puis on vérifie avec ip a que l'interface a bien les addresses ip et est à l'état haut :


On voit que ç'est le cas. En utilisant le programme ether fourni en TP de réseau, nous allons regarder les paquets passant sur l'interface usb0 tout en effectuant un ping sur l'addresse 10.0.0.2.


Finalement on voit que la carte fonctionne : elle reçoit le ping envoyé par le pc et répond. On peut s'atteler à la suite.

Création du protocole

Voici la structure de notre Protocole Ethernet, elle est fortement inspiré de la structure d'un paquet ARP. L'opération/commande sera le premier octet dans les données, suivi d'éventuels arguments supplémentaires.

typedef struct
		{
			uint16_t      Operation;/**< Type of operation, either PROTO_OPERATION_REQUEST or PROTO_OPERATION_REPLY */
            uint16_t ProtocolType; /** ETHERTYPE_PROTO**/
			MAC_Address_t Sender_MACADD; /**< Sender's hardware address */
			MAC_Address_t Target_MACADD; /**< Target's hardware address */
            uint16_t      Length;
            uint8_t      Data[MAX_COMMAND];

		} Proto_Header_t;

Cette structure a été ajoutée dans un nouveau fichier appelé Proto.h accompagné de son .c . Dans ce .c, on crée une fonction Proto_ProcessIPPacket(void* InDataStart, void* OutDataStart) (mauvais nom de fonction, il n'y a pas d'IP)qui enverra une réponse lorsque la carte reçoit un paquet. Pour que ce protocole soit effectivement traité, il faut inclure ce fichier dans Ethernet.c, et ajouter un cas correspondant à notre protocole dans le traitement de paquet. On ajoute le protocole en ajoutant la ligne

#define ETHERTYPE_PROTO                    0x8888

dans EthernetProtocols.h. Ensuite, on doit créé une fonction DecodeProtoHeader dans ProtocolDecoders.c, comme pour les autres protocoles déjà existants, en l'adaptant à la structure de protocole choisi.

Pour alléger le programme, nous enlevons les autres protocoles qui ne nous serons pas utiles dans le Makefile et sur les fichiers déjà cités.

On upload le résultat sur la carte RNDIS, on remet l'interface à l'état haut. On veut maintenant utiliser ether mais il y a un problème : ce programme ne connaît pas notre protocole. Nous allons devoir le modifier pour qu'il corresponde à nos besoins.

Modification de ether

On doit, dans bpf.c, remplacer le protocole dummy (qui est un protocole non utilisé et destiné à être remplacé) par le nôtre. Ensuite, nous allons faire en sorte que les paquets reçus soient enregistrés dans des fichiers textes, de sorte à ce qu'ils puissent être analysés par la suite.

Vidéo montrant une led clignoter quand nous recevons un paquet avec notre protocole Ethernet (0x8888)
Vous pouvez retrouver notre ether customisé dans notre git à la racine

S8-Pico-Binome-7/Programs/ListeningEther/customether

En envoyant des paquets avec ether -s suivant notre protocole, on constate bien que la carte RNDIS renvoie un paquet réponse forgé par la fonction Proto_ProcessIPPacket et que ce dernier est stocké dans un fichier à chaque fois.

Envoi de paquet

Maintenant que la carte est capable de répondre à un paquet suivant notre protocole, nous crééons une fonction int16_t Proto_SendIPPacket(void*OutDataStart, uint8_t data[MAX_COMMAND]) (là encore, nom mal choisi) dans Proto.c, qui permet d'envoyer spontanément un paquet suivant notre protocole. Cela se fait grâce à FrameOut. Lorsque l'on ajoute un paquet dans FrameOut, celui-ci est envoyé automatiquement par la carte grâce à la LUFA. Dans la fonction Proto_SendIPPacket, nous allons construire un paquet contenant les données data. Celui ci sera alors envoyé par la carte.

Pour la suite, nous avons eu des problèmes. Il s'agissait d'ajouter un ISR et la communication SPI sur la LUFA. Pour cela, nous avons dû ajouter un bit à 1 sur SPCR : SPCR |= (1<<SPIE); Pour activer les interruptions sur la SPI. Ensuite, dans le fichier RNDISEthernet.c, nous ajoutons un ISR qui va donc s'activer chaque fois qu'une commande est reçue pour la traiter. Pour tester, nous avons d'abord essayé d'envoyer des paquets avec des données incrémentant de 1 à chaque octet, chaque fois qu'une commande SPI est reçue. En dernier octet des données se trouve un compteur de paquets comptant les paquets envoyés.

Packetwitdata.png

En faisant cela, et en utilisant notre ether modifié, on constate que ça fonctionne, seulement nous avons des pertes inexpliqués: le compteur de paquets passe de manière aléatoire des paquets. Deux causes nous semble possibles : soit le délai entre deux envois de paquets est trop court, soit quelque chose dans la LUFA fait que l'ISR n'est pas appelé à chaque fois. En ajoutant un xor sur une led à chaque appel de l'ISR, et en envoyant un ordre toutes les secondes via la carte mère, nous constatons que la LED clignote deux fois plus lentement qu'elle devrait. Il est donc possible que nous ayons également un problème de configuration de fréquence sur la carte réseau.


Nous essayons alors de faire un programme tout simple pour la carte réseau en mettant un ISR (dans ./Programs/TestsSPI/Slave). En utilisant le programme maître fourni par Monsieur Redon (dans PingPongSPI), nous constatons que l'envoi et la réception de commande avec l'ISR fonctionne (nous avons bien la même chose que dans le test SPI avec Pong), mais la LED clignote quand même deux fois plus lentement que ce qu'elle devrait), et nous ne savons pas comment expliquer ce phénomène.


Notre méthode fonctionne donc bien mais nous avons à priori un problème dans notre application de celle-ci.

Le but était par la suite d'introduire une machine à états dans l'ISR:

  • Un état LISTENING qui attend un ordre
  • Un état pour chaque commande demandée qui attend la réponse du PC puis qui la traduit en une réponse SPI pour la carte mère. Une fois l'état fini, on revient à l'état Listening.

Grâce à cela, nous aurions pû gérer chaque commande envoyée par la carte mère puis faire en sorte que la carte réseau ait le comportement approprié.

Décodage des paquets de l'ordinateur

A la racine S8-Pico-Binome-7/Programs/SPIfichierDistants/PC/ProtoPC.c de notre git, se trouve le code permettant à l'ordinateur d'interpréter les paquets réseau envoyé par la carte RNDIS. Les paquets RNDIS sont enregistrés/écrasés dans des fichiers texte sur le PC. Ces fichiers textes sont décodés par le code et décortiqués. Chaque capsule du paquet et enregistre chaque partie de des capsules Ethernet et de notre Protocole Personnalisé dans des variables pour être réutilisés plus tard. Par exemple, on enregistre les adresses mac destination et sources pour les inverser lors du renvoie du paquet. Ou encore l'enregistrement de la commande (1er octet des données) qui est ensuite interprété en "ls". La suite des données est ensuite interprété comme le path à exécuté avec le "ls".

paquet réseau exemple
paquet réseau exemple
Les deux premières ligne sont notre paquet.txt. Notre code décortique ensuite chaque partie des capsules Ethernet/Notre Protocole et les enregistre et les print.

Vous pouvez aussi voir l'interprétation des données en ASCII. Ces données retranscrites en ASCII sont ensuite utilisés pour exécuté un ls. Le résultat de ce ls sera ensuite enregistré dans un autre fichier texte qui sera retransformé en paquet Réseau Ethernet encapsulation notre Proto. On enverra ensuite chaque nom de fichier dans ce fichier texte un par un avec la commande 0x11 pour dire à la carte réseau qu'il y a encore un fichier.

Limitations dû à la SPI

Nous avions un bon rythme de travail, dû à la conception du Shield et à d'autres problèmes rencontrés, nous avons été ralenti par ces problèmes. Une fois ces problèmes réglés nous avons pu aider les autre élèves à les surpasser pour qu'ils pussent avancer de leur coté.

Test de la SPI avec PONG

Dû a l'erreur causé par le redresseur et la communication SPI, Monsieur REDON nous a donné un code pong.c qui communique par SPI entre la carte réseau et le Shield. Le Shield envoie un octet et la carte-réseau renvoie l'octet du coup d'horloge précédent. Il y a un problèmes, les câbles SPI reliant nos cartes sont défectueux et peuvent parfois renvoyés un octet qui n'a pas lieu d'être. Par exemple, nous envoyons un octet de 16 et nous recevons au coup d'horloge suivant, 192, 108 ou encore 65,..., qui ne sont pas des octets envoyables par le code pong.c. Ces cas sont rares mais ils peuvent amener à des problèmes de communication de paquets réseaux

Pong montrant la comm SPI entre le shield et la carte RNDIS
Pong montrant la comm SPI entre le shield et la carte RNDIS
Voici un exemple de la fonction PONG fonctionnelle
Schéma, PCB & KiCAD

Shield

Photos et vidéos description
Carte-mère soudée.jpg Le shield soudée avec juste le BootLoader dans le microP

Carte RNDIS

Nous avons choisi de réaliser la carte réseau RNDIS, car nous pensons que ce projet était aussi en lien avec nos cours de réseau et de système d'exploitation, cette carte était pour nous un moyen d'en apprendre plus sur ces aspects.

La première chose à faire était de réaliser la carte électronique. Pour cela, des informations nous sont fournies. On sait alors que le microcontrôleur à utiliser doit avoir des capacités USB et que l'on peut utiliser soit un ATMega16u2, un ATMega32u4 ou un AT90USB suivant la mémoire que l'on veut disposer. Nous avons choisi d'utiliser un AT90USB1286-A pour sa mémoire plus grande. Nous avons pu observer sur les projets SE4 de l'année dernière que les élèves n'avait pas assez de mémoire pour des paquets réseaux importants.

Ensuite, nous avons commencé à faire le schéma électrique de la carte réseau. Nous avons commencé à mettre les composants pour faire fonctionner le microcontrôleur de la même façon que sur le projet de SE3. Après cela, nous avons commencé à faire les entrées et sorties. On sait que la carte va communiquer avec la carte mère via un connecteur HE10, des signaux MISO, MOSI, SCK et CS sont alors à connecter au microcontrôleur. Nous avons choisi d'utiliser les ports suivants :

SCHEMATIQUE de la Carte RNDIS
PCB de la carte RNDIS
Connecteur USB permettant l'ALIM de la carte en solo et le transfert DATA en réseau avec un ordinateur connecté à Internet
Connecteur USB permettant l'ALIM de la carte en solo (sans shield et carte-mère) et le transfert de DATA

en réseau avec un ordinateur connecté à Internet.

Dû à une erreur de design, la carte réseau ne peut être alimentée qu'avec la carte mère alimentée

Carte RNDIS soudée
Carte RNDIS soudée
visu 3D RNDIS
visu 3D RNDIS
Erreur de design
PIN ALIM non connecté
PIN ALIM non connecté
Comme vous pouvez l'observer, le pin ALIM de notre Carte RNDIS n'est pas connecté avec les pins VCC.

Par conséquent, notre carte carte RNDIS ne peut-être alimentée que quand,

le Shield où la carte mère est alimentée en 5V.

Solution : connecter cette PIN ALIM avec les VCC en plus de la PIN ALIM de l'USB + mettre un cavalier pour basculer entre l'alimentation par la carte-mère où directement par USB

PIN ALIM non connecté USB
PIN ALIM non connecté USB
PINOUT
PIN UTILITY PIN NAME
ChipSelect PB0
CLK/SCK PB1
MOSI PB2
MISO PB3
Pin d'Interruption PB4
LED[1-4] PC[0-3]

Conclusion

En conclusion, ce projet nous a permis de mettre en application les différentes parties du programme de ce semestre. Nous avons revu la CAO, avons vu en détail comment l'ordonnancement fonctionnait et comment les éléments constituant des échanges réseaux intéragissaient.

Nous avons réussi à effectuer toutes les communications nécessaires au projet final, en faisant cela nous avons une preuve que nous pouvons, à partir de notre travail, concevoir le soft prenant en charge toutes les commandes demandées.

Cependant, ayant rencontrés de nombreux problèmes en essayant de faire fonctionner ces interactions (problème sur le releveur de niveau, problème de perte de paquets, ...) nous n'avons pas pu automatiser ces différentes interactions pour concevoir la LUFA finale.

Malgré tout, grâce à cela, nous avons beaucoup mis à l'épreuve notre capacité à résoudre des problèmes sur tous les plans (électronique et informatique) et cela nous a sans doute plus appris que si nous n'avions eu aucun problème et avions réussi du premier coup chaque partie du projet.

NOTES

deux ports USB pour la carte fille : un pour la connexion en ISP/Réseau à l'ordinateur et un pour la programmation. Possibilité de faire une connexion SPI avec un câble RJ45

Ressources & Sources

Lien Git : https://gitea.plil.fr/rboursau/S8-Pico-Binome-7