Message Queue for RTOS pour microcontrôleurs

10

J'écris actuellement un RTOS pour les microcontrôleurs. Le tout est écrit en C ++ 11 - si quelqu'un est intéressé, et le lien vers le référentiel est en bas.

Actuellement, j'écris une classe qui est une simple file d'attente de données pour passer des objets entre des threads (ou entre des gestionnaires d'interruption et des threads ou des gestionnaires d'interruption et d'autres gestionnaires d'interruption). Habituellement, j'essaie de suivre certaines API communes trouvées sur d'autres projets, mais je n'ai trouvé aucun exemple de file d'attente simultanée ayant une emplace()fonction ET prenant en charge les délais d'attente.

Mon "problème" général est que je ne peux pas choisir entre ces deux interfaces:

( std::chrono::duration<Rep, Period>est un type basé sur un modèle, j'omet le modèle standard pour plus de clarté)

Première version:

template<typename T>
class FifoQueue
{
public:
    ...
    template<typename... Args>
    int tryEmplaceFor(std::chrono::duration<Rep, Period>, Args&&... args);
    int tryPopFor(T&, std::chrono::duration<Rep, Period>);
    int tryPushFor(const T&, std::chrono::duration<Rep, Period>);
    int tryPushFor(T&&, std::chrono::duration<Rep, Period>);
    ...
}

Deuxième version:

template<typename T>
class FifoQueue
{
public:
    ...
    template<typename... Args>
    int tryEmplaceFor(std::chrono::duration<Rep, Period>, Args&&... args);
    int tryPopFor(std::chrono::duration<Rep, Period>, T&);
    int tryPushFor(std::chrono::duration<Rep, Period>, const T&);
    int tryPushFor(std::chrono::duration<Rep, Period>, T&&);
    ...
}

(il y aura un deuxième ensemble de ces fonctions avec ...Untilsuffixe - celles-ci utiliseraient le point temporel au lieu de la durée)

La première version suit un "style commun" consistant à avoir le délai d'expiration comme dernier paramètre (les exemples sont les files d'attente de messages POSIX std::condition_variable, les files d'attente simples dans n'importe quel RTOS pour les microcontrôleurs). Le problème est qu'il n'est pas possible d'avoir cet argument timeout comme dernier argument pour la fonction tryEmplaceFor (), car dans le cas de modèles variadiques, les arguments "connus" doivent être les premiers (*). La deuxième version est donc "cohérente" - toutes les fonctions avec timeout ont le timeout comme premier argument. Cette variante a un problème évident d'être probablement le premier exemple de délai d'expiration comme premier argument pour une telle fonctionnalité.

Quelle interface servirait mieux le système d'exploitation:

  • norme établie pour avoir le délai d'expiration comme dernier argument (à l'exception de tryEmplaceFor()et tryEmplaceUntil()- où il doit être le premier argument (*))?
  • cohérence - préférez le délai d'expiration comme premier argument?

(*) - Je sais que je pourrais techniquement avoir le délai d' attente en dernier argument en faveur tryEmplaceFor()et tryEmplaceUntil(), mais je préfère éviter d' utiliser une telle magie de modèle pour un tel scénario simple - faire toutes ces instanciations récursives juste pour obtenir le dernier argument semble un peu exagéré, surtout quand je visualise les erreurs que le compilateur produirait au cas où l'utilisateur ferait quelque chose de mal ...


Freddie Chopin
la source
Quelle est la différence entre la première et la deuxième version? Veuillez mettre en évidence.
JBRWilkinson
1
Observation: tout le monde ne connaît pas assez bien POSIX pour être gêné par le placement du temps, mais tous ceux qui utilisent votre interface seront frustrés par l'API incohérente. Je vote # 2.
J Trana

Réponses:

0

Comme suggéré par une réponse qui a été supprimée (malheureusement) et des commentaires, j'ai suivi la ligne "cohérence" (deuxième variante présentée) - dans toutes les fonctions "essayer ... Pour" et "essayer ... Jusqu'à" le délai d'expiration (durée ou point de temps) est le premier argument.

Ceci est le code au stade actuel - lien

Freddie Chopin
la source