Contiki: Écrire le programme pour le contrôleur de capteur (CC26xx)

Créé le 24 déc. 2016  ·  16Commentaires  ·  Source: contiki-os/contiki

Salut!
J'aimerais écrire un programme de gestion des capteurs pour le contrôleur de capteur (AUX) du CC2650. Pour autant que je sache, je dois utiliser Sensor Controller Studio (SCS) pour ce faire. Ensuite, je dois écrire l'application Contiki pour le processeur principal. Et ces deux programmes peuvent interagir via des sémaphores et une RAM AUX.

  • Est-ce correct?
  • Puis-je écrire un programme AUX dans le référentiel Contiki (sans avoir besoin de SCS) ?
  • Si j'ai un programme généré par SCS, de quoi ai-je besoin pour compiler le fichier binaire total du programme Contiki et AUX (à télécharger sur la puce) ?
Platform / CPU / ARM / CC13xx-CC26xx

Commentaire le plus utile

Merci pour vos instructions @tarakanov Très utile ! Il semble que vous ayez découvert une incompatibilité de contiki avec CC1350 AUX. Une autre façon de résoudre le problème consiste à ne PAS désactiver RTC_CH2

if(ti_lib_aon_rtc_event_get(AON_RTC_CH2)) {
/* après le sommeil; puisqu'un rtimer est déjà programmé, ne faites rien */
// ti_lib_aon_rtc_channel_disable(AON_RTC_CH2) ;
HWREG(AON_RTC_BASE + AON_RTC_O_EVFLAGS) = AON_RTC_EVFLAGS_CH2 ;
}

J'ai creusé un peu plus et j'ai découvert qu'aux_ctrl_register_consumer() déclenche AONWUC_AUX_WAKEUP, ce qui fait que soc_rtc.c désactive AON_RTC_CH2. Ma question ici est de savoir pourquoi contiki (soc-rtc.c) désactive AON_RTC_CH2. Ce qu'il fait, c'est de tuer toutes les interruptions de l'AUX, immédiatement après l'avoir réveillé.

Ce qui m'amène à la question - Est-il sûr de désactiver AON_RTC_CH2. Est-ce qu'un autre code de l'environnement contiki l'utilise ?

Tous les 16 commentaires

Oui c'est correct. Je suggérerais d'utiliser SCS car il est beaucoup plus facile à utiliser, mais il est possible d'écrire des programmes pour le contrôleur de capteur sans utiliser SCS. Le processeur principal devra charger le programme dans la RAM du contrôleur de capteur. Suggérez de regarder les formations sur les contrôleurs de capteurs ici : ti.com/simplelinkacademy

Merci @jonnteolsson. J'ai réussi à écrire un programme en SCS. L'ADC et le code d'événement fonctionnent bien dans le test de tâche de SCS. Maintenant, je dois inclure ce programme dans Contiki. La Simplelink Academy de TI a décrit ce processus pour TI-RTOS, mais pas pour Contiki. De quoi ai-je besoin pour importer ces fichiers dans Contiki et les compiler ?

En ce qui concerne le port Contiki de CC26xx, il existe un mécanisme pour interagir avec AUX, mais je ne trouve aucune information sur l'inclusion du code d'application AUX dans Contiki.

Vous pouvez utiliser SCS pour générer un code bare-metal à l'aide de CCS.

L'intégration avec contiki est très simple.

Vous verrez qu'il va générer un code d'initialisation (que vous pouvez exécuter onde
n'importe où sur contiki) et quelques interruptions (qui peuvent idéalement déclencher des événements dans
contiki pour signaler votre candidature).

Nous l'utilisons depuis un certain temps sans aucun problème avec contiki et
avec d'autres RTOS.

Marco Casaroli

Le mer. 28 décembre 2016 à 10h43, Semyon Tarakanov < [email protected]

a écrit:

Merci @jonnteolsson https://github.com/jonnteolsson . j'ai réussi
écrire un programme en SCS. L'ADC et le code d'événement fonctionnent bien dans le test de tâche de
SCS. Maintenant, je dois inclure ce programme dans Contiki. Simplelink de TI
Academy a décrit ce processus pour TI-RTOS, mais pas pour Contiki. Qu'est-ce que je
besoin d'importer ces fichiers dans Contiki et de les compiler ?

Pour autant que je regarde à travers le port Contiki de CC26xx, il existe un mécanisme pour
interagir avec AUX, mais je ne trouve aucune information sur l'inclusion d'AUX
code d'application à Contiki.

-
Vous recevez ceci parce que vous êtes abonné à ce fil.
Répondez directement à cet e-mail, consultez-le sur GitHub
https://github.com/contiki-os/contiki/issues/2019#issuecomment-269472189 ,
ou couper le fil
https://github.com/notifications/unsubscribe-auth/ADszaHFjy9moPwSfd4zUiZOkQhfYw29lks5rMlljgaJpZM4LVLeg
.

En plus de copier le code dans la RAM du contrôleur de capteur et de démarrer le contrôleur, je suppose que vous avez également besoin de code pour que le MCU principal puisse gérer les événements du contrôleur. Je pense également que vous auriez à manipuler les horloges dans AUX afin que le contrôleur puisse continuer à fonctionner pendant que le reste de la puce est éteint.

Marco, as-tu eu à faire ces manipulations d'horloge et de puissance ?

Bonjour George.

D'après mon expérience, le code généré fait déjà le lpm et les horloges
initialisation

Je dois vérifier s'il y avait quelque chose que nous devions changer dans contiki lpm
code mais je pense que nous ne l'avons pas fait.

Je n'ai pas d'ordinateur disponible en ce moment pour que je puisse vérifier. je posterai
quelques instructions sur la façon de le faire en janvier.

BR

Le mer. 28 décembre 2016 à 11:25 George Oikonomou [email protected]
a écrit:

En plus de copier le code dans la RAM du contrôleur de capteur et de démarrer le
contrôleur, je suppose que vous avez également besoin de code pour que le MCU principal puisse gérer
événements du contrôleur. Je pense aussi qu'il faudrait manipuler
horloges dans AUX afin que le contrôleur puisse continuer à fonctionner pendant que le reste du
la puce est hors tension.

Marco, as-tu eu à faire ces manipulations d'horloge et de puissance ?

-
Vous recevez ceci parce que vous avez commenté.

Répondez directement à cet e-mail, consultez-le sur GitHub
https://github.com/contiki-os/contiki/issues/2019#issuecomment-269476639 ,
ou couper le fil
https://github.com/notifications/unsubscribe-auth/ADszaEI9Bcop7xjSvKmKZEYgQWan2tLnks5rMmNBgaJpZM4LVLeg
.

J'ai "en quelque sorte" intégré le SC avec Contiki, mais je rencontre quelques problèmes.
J'utilise le code d'émulation SC UART et je ne peux obtenir qu'environ 6 à 8 caractères TX sans corruption.
Curieusement, RX fonctionne absolument parfaitement.
Mon init de code de test (basé sur cc26xx-demo.c) ressemble à ceci :
`static aux_consumer_module_t uart_aux = {
NULL, AUX_WUC_SMPH_CLOCK | AUX_WUC_AIODIO0_CLOCK |
AUX_WUC_AIODIO1_CLOCK | AUX_WUC_TIMER_CLOCK |
AUX_WUC_ANAIF_CLOCK | AUX_WUC_TDCIF_CLOCK |
AUX_WUC_OSCCTRL_CLOCK | AUX_WUC_ADI_CLOCK | AUX_WUC_TDC_CLOCK |
AUX_WUC_ADC_CLOCK | AUX_WUC_REF_CLOCK
} ;

/ ------------------------------------------------- -------------------------- /
PROCESS_THREAD(cc26xx_my_process, ev, données)
{

PROCESS_DEBUT();
printf("CC26XX test v43\n");
// à utiliser dans le rappel d'alerte pour RX
softuart_event = process_alloc_event();

ti_lib_sys_ctrl_power_everything();

// Arrête SC.
ti_lib_aon_wuc_aux_image_invalid();

// Exécute toutes les horloges à pleine vitesse pour le moment.
ti_lib_prcm_inf_clock_configure_set(PRCM_CLOCK_DIV_1, PRCM_RUN_MODE);
ti_lib_prcm_inf_clock_configure_set(PRCM_CLOCK_DIV_1, PRCM_SLEEP_MODE);
ti_lib_prcm_inf_clock_configure_set(PRCM_CLOCK_DIV_1, PRCM_DEEP_SLEEP_MODE);
// ressources d'horloge
aux_ctrl_register_consumer(&uart_aux);
AUXWUCClockFreqReq(AUX_WUC_CLOCK_HIFREQ);
AUXWUCPowerCtrl(AUX_WUC_POWER_ACTIVE);
aux_ctrl_power_up();
// accès au domaine AUX
scifOsalEnableAuxDomainAccess();
// Initialisation du pilote SC
scifInit(&scifDriverSetup);
// Démarrer l'émulateur UART
scifExecuteTasksOnceNbl(BV(SCIF_UART_EMULATOR_TASK_ID));
// Activer la génération du débit en bauds
scifUartSetBaudRate(9600);
// mon rappel d'alerte
scifOsalRegisterTaskAlertCallback(&uartAlertCallback);
// Activer RX (10 périodes de bit inactif requises avant d'activer la détection de bit de démarrage)
scifUartSetRxFifoThr(SCIF_UART_RX_FIFO_MAX_COUNT / 2);
scifUartSetRxTimeout (10 * 2);
scifUartSetRxEnableReqIdleCount (10 * 2);
scifUartRxEnable(1) ;

// Activer les événements (FIFO RX à moitié plein ou délai d'attente de 10 bits
scifUartSetEventMask(BV_SCIF_UART_ALERT_RX_FIFO_ABOVE_THR | BV_SCIF_UART_ALERT_RX_BYTE_TIMEOUT);

scifUartTxPutChars("Bonjour, comment ça va ? C'est une longue chaîne\r\n",47);
`
Un peu plus de mes essais précédents est sur un post a fait sur le forum de TI :
https://e2e.ti.com/support/wireless_connectivity/zigbee_6lowpan_802-15-4_mac/f/158/p/567025/2088653#2088653
Des idées de ce qui pourrait tuer mon TX ? semble que la minuterie utilisée pour le débit en bauds s'arrête, mais depuis que j'ai déclaré l'utilisation de AUX_WUC_TIMER_CLOCK, ne devrait-elle pas être protégée?

OK, le code que j'ai posté auparavant fonctionne en effet comme un charme pour l'émulation UART dans Contiki via le contrôleur de capteur.
Mon problème de transmission ? interface USB<->UART mourante connectée aux broches d'émulation UART ; remplacé par un autre, même avec le même chipset, et le tour est joué ! Cela fonctionne parfaitement, donc oui, aux_ctrl_register_consumer() empêche effectivement toute mise hors tension des horloges requises sur le SC.
J'ai inclus toutes les horloges AUX, qui, je pense, doivent être ajustées à ce que le code UART utilise, mais cela fonctionne.

D'ACCORD. Ce n'est pas si facile de faire cette chose. Voici mes deux petites étapes. D'abord, j'écris le programme le plus simple pour Sensor Controller dans SCS et j'utilise uniquement le code d'exécution avec une ligne de code :
gpioSetOutput(AUXIO_O_LED_DP1);
Après la génération de code, je prends ces fichiers dans Contiki (dans le répertoire platform/srf06-cc26xx/sensortag ):

scif.c
scif.h
scif_framework.c
scif_framework.h
scif_osal_none.c
scif_osal_none.h

Je les inclus dans la construction en ajoutant BOARD_SOURCEFILES += scif_framework.c scif_osal_none.c scif.c au fichier Makefile.sensortag . Ensuite, j'ajoute un processus au projet Contiki (je modifie cc26xx-demo.c ) avec ce morceau de code :

#include "aux-ctrl.h"
#include "scif.h"
#define BV(x)    (1 << (x))

//Other code here

static aux_consumer_module_t blink_aux = {NULL, AUX_WUC_SMPH_CLOCK };
PROCESS_THREAD(cc26xx_demo_process, ev, data)
{
  PROCESS_BEGIN();
  printf("CC26XX demo\n");
  aux_ctrl_register_consumer(&blink_aux);
  scifInit(&scifDriverSetup);
  scifExecuteTasksOnceNbl(BV(SCIF_BLINK_TASK_ID));

// Other code here

Puis make TARGET=srf06-cc26xx BOARD_SENSORTAG=1 BOARD=sensortag/cc2650 BOARD_CONF_DEBUGGER_DEVPACK=1 . Avec ce code, Sensortag allumera la LED (j'ai attaché la LED au DP0 de la carte DevPack). Je pense donc que c'est le programme d'intégration minimale.

Pour ma deuxième étape, j'ai essayé d'itérer le code d'exécution avec planification. Pour itérer sur le code d'exécution, vous devez ajouter fwScheduleTask(1); pour planifier la prochaine itération en un seul clic. Le temps de tick est défini par Contiki en invoquant selfStartRtcTicksNow(0x00010000); Le temps de tick est défini entre parenthèses au format 16,16 bits. Par exemple, 0x00010000 correspond à 1 seconde.
Le code d'exécution est (et cela fonctionne bien dans SCS) :

U16 buttonState; //attach button to DP0 of DevPack
gpioGetInputValue(AUXIO_I_BUTTON_DP0; buttonState);

if (buttonState == 1) {
  gpioClearOutput(AUXIO_O_LED_DP1);
} else {
  gpioSetOutput(AUXIO_O_LED_DP1);
}
fwScheduleTask(1);

Code du projet Contiki :

#include "aux-ctrl.h"
#include "scif.h"
#define BV(x)    (1 << (x))

//Other code here

static aux_consumer_module_t blink_aux = {NULL, AUX_WUC_SMPH_CLOCK };

PROCESS_THREAD(cc26xx_demo_process, ev, data)
{
  PROCESS_BEGIN();
  printf("CC26XX demo\n");
  aux_ctrl_register_consumer(&blink_aux);
  scifInit(&scifDriverSetup);
  selfStartRtcTicksNow(0x00010000);
  scifExecuteTasksOnceNbl(BV(SCIF_BLINK_TASK_ID));

// Other code here

Ce code doit vérifier l'état du bouton toutes les 1 seconde et allumer la led. Mais il échoue. En fait, si vous appuyez sur le bouton pendant la mise sous tension de la carte, SC le verra et allumera la LED. Il indique qu'une itération du code d'exécution a été effectuée. Puis quelque chose s'est produit - le code a échoué ou la planification a échoué.
SCS indique que fwScheduleTask() utilise le canal 2 AON_RTC en mode de comparaison continue pour générer des réveils périodiques pour l'AUX. Le réglage du canal RTC 2 se fait via selfStartRtcTicksNow(); et cela ne semble pas poser de problème (à partir du code). Contiki utilise le canal RTC 0 et le canal 1 (à partir de soc-rtc.c ). Je pense également que le code d'exécution devrait être itéré même sans un tel calendrier.

Je suis donc bloqué ici. Est-ce que quelqu'un a réussi avec ça ?

salut @tarakanov , je suis bloqué au même poste dans votre message précédent. Je voulais vérifier si vous aviez fait des progrès avec ça?

Je parviens à exécuter l'image SC périodiquement. Rappelez-vous, pour exécuter le code d'exécution, vous devez ajouter fwScheduleTask(1) pour un tick. Le temps de tick est défini par Contiki en appelant selfStartRtcTicksNow(0x00010000) . Le temps de tick est défini entre parenthèses au format 16,16 bits. Par exemple, 0x00010000 correspond à 1 seconde. Après cette configuration, vous devez réellement lancer l'exécution en appelant scifStartTasksNbl(BV(SCIF_BLINK_TASK_ID)) avec le nom de la tâche comme argument. Mais n'appelez pas scifExecuteTasksOnceNbl comme je l'ai mentionné plus tôt, car il exécutera la tâche une fois et ne configurera pas d'événements pour la prochaine itération. Voici une partie du code Contiki :

  PROCESS_BEGIN();
  printf("CC26XX demo\n");
  aux_ctrl_register_consumer(&blink_aux);
  scifInit(&scifDriverSetup);
  scifStartRtcTicksNow(0x00010000);
  scifStartTasksNbl(BV(SCIF_BLINK_TASK_ID));

Mais il est en conflit avec le gestionnaire d'interruption AON RTC dans le code soc-rtc.c . Les temporisateurs logiciels RTC utilisent le canal RTC 0 et le canal 1 mais soc_rtc_isr() est programmé pour capturer les événements combinés des trois canaux (ch0, ch1, ch2) avec cette commande :
ti_lib_aon_rtc_combined_event_config(AON_RTC_CH0 | AON_RTC_CH1 | AON_RTC_CH2)
Et lorsque vous configurez correctement l'image SC et l'exécutez pour la première fois, RTC ch2 déclenchera un événement après le temps de tick qui appellera également cette routine. Et cette routine désactivera RTC ch2 avec ce code :

  if(ti_lib_aon_rtc_event_get(AON_RTC_CH2)) {
    /* after sleep; since a rtimer is already scheduled, do nothing */
    ti_lib_aon_rtc_channel_disable(AON_RTC_CH2);
    HWREG(AON_RTC_BASE + AON_RTC_O_EVFLAGS) = AON_RTC_EVFLAGS_CH2;
  }

Je change l'événement de combinaison en celui-ci, et soc_rtc_isr ne gérera pas les événements de ch2 :
ti_lib_aon_rtc_combined_event_config(AON_RTC_CH0 | AON_RTC_CH1)

@g-oikonomou s'il vous plaît aviser ici. Si Contiki n'utilise que ch0 et ch1 pour les minuteries, peut-être est-il bon de supprimer toutes les utilisations de ch2 de soc-rtc.c ?

J'arrive à faire une alerte à Contiki via des événements. Pour alerter le noyau principal, vous devez ajouter fwGenAlertInterrupt(); dans la tâche d'exécution. Lorsque vous initialisez SC dans Contiki, vous devez enregistrer la fonction de rappel pour cette alerte :

  scifOsalRegisterTaskAlertCallback(scTaskAlertCallback);
  scifInit(&scifDriverSetup);

La fonction de rappel allouera l'événement au processus ( scinterrupt_test_process dans mon cas):

process_event_t sc_event;
void scTaskAlertCallback(void)
{
    scifClearAlertIntSource();
    sc_event = process_alloc_event();
    process_post(&scinterrupt_test_process, sc_event, NULL);
    scifAckAlertEvents();
}

Ensuite, vous pouvez identifier cet événement par son nom :

    PROCESS_YIELD();
     if (ev == sc_event) {
        printf("Hello from SC\n");
    }

sc_event = process_alloc_event();

Cette expression ne doit être faite qu'une seule fois, dans le code d'initiation. Il attribue un numéro unique qui représente ces événements du contrôleur de capteur.

Hmm ...
scTaskAlertCallback() exécuté pendant une interruption ? Si c'est le cas, il ne doit pas utiliser process_post() . Seul process_poll() est sûr pour les gestionnaires d'interruption.

Si c'est le cas, il ne doit pas utiliser process_post(). Seul process_poll() est sans danger pour les gestionnaires d'interruption.

Je n'en suis pas si sûr, process_post() est asynchrone. La différence est que nous pouvons déclencher un événement spécifique, alors qu'avec process_poll() nous envoyons toujours le même événement générique "sondage"

Je n'en suis pas si sûr, process_post() est asynchrone.

D'ACCORD. J'ai revu le code. Maintenant, je pense que vous avez raison. process_post() peut "interrompre" do_event() sans causer de problèmes.

Merci pour vos instructions @tarakanov Très utile ! Il semble que vous ayez découvert une incompatibilité de contiki avec CC1350 AUX. Une autre façon de résoudre le problème consiste à ne PAS désactiver RTC_CH2

if(ti_lib_aon_rtc_event_get(AON_RTC_CH2)) {
/* après le sommeil; puisqu'un rtimer est déjà programmé, ne faites rien */
// ti_lib_aon_rtc_channel_disable(AON_RTC_CH2) ;
HWREG(AON_RTC_BASE + AON_RTC_O_EVFLAGS) = AON_RTC_EVFLAGS_CH2 ;
}

J'ai creusé un peu plus et j'ai découvert qu'aux_ctrl_register_consumer() déclenche AONWUC_AUX_WAKEUP, ce qui fait que soc_rtc.c désactive AON_RTC_CH2. Ma question ici est de savoir pourquoi contiki (soc-rtc.c) désactive AON_RTC_CH2. Ce qu'il fait, c'est de tuer toutes les interruptions de l'AUX, immédiatement après l'avoir réveillé.

Ce qui m'amène à la question - Est-il sûr de désactiver AON_RTC_CH2. Est-ce qu'un autre code de l'environnement contiki l'utilise ?

Cette page vous a été utile?
0 / 5 - 0 notes

Questions connexes

alignan picture alignan  ·  10Commentaires

remyleone picture remyleone  ·  3Commentaires

hamidshabanipour picture hamidshabanipour  ·  4Commentaires

ragbagger16 picture ragbagger16  ·  10Commentaires

alejandr0 picture alejandr0  ·  12Commentaires