Changes between Version 6 and Version 7 of MjpegCourse/Monopro
- Timestamp:
- Feb 26, 2008, 3:59:54 AM (17 years ago)
Legend:
- Unmodified
- Added
- Removed
- Modified
-
MjpegCourse/Monopro
v6 v7 19 19 20 20 La seconde partie du TP vous permettra d'utiliser DSX pour décrire et 21 contrôler précisément le déploiement de l'application logicielle !SplitMsg 22 (TCG décrit avec DSX),sur l'architecture matérielle décrite dans la première23 partie. On validera ce déploiement en simulant l'exécution d >u code binaire24 de l'application logicielle (généré par DSX)sur le modèle SystemC de25 l'architecture matérielle (également généré par DSX).21 contrôler précisément le déploiement de l'application logicielle !SplitMsg, 22 sur l'architecture matérielle décrite dans la première 23 partie. On validera ce déploiement en simulant l'exécution du code binaire 24 de l'application logicielle sur le modèle SystemC de 25 l'architecture matérielle. 26 26 27 27 La troisième partie du TP vous permettra d'atteindre notre véritable but, qui est … … 44 44 la latence du réseau: nombre minimal de cycles pour une traversée du réseau 45 45 "one-way". 46 * Elle comporte un contrôleur de verrous (composant LOCKS), utilisé pour protéger47 l'accès aux canaux de communication MWMR.48 46 * Elle comporte deux contrôleurs mémoire RAM0 et RAM1 49 47 * Elle comporte un contrôleur de terminal TTY. … … 72 70 #!/usr/bin/env python 73 71 74 from dsx import * 75 from soclib import * 72 import soclib 76 73 from vgmn_noirq_mono import VgmnNoirqMono 77 74 78 75 archi = VgmnNoirqMono() 79 76 80 archi.generate(Caba()) 81 }}} 82 * Rendez ce nouveau fichier de description exécutable, lancez-le. Ne réalisez pas la compilation 83 de la plateforme résultante: nous n'avons pas encore de logiciel à exécuter dedans. 77 archi.generate(soclib.PfDriver()) 78 }}} 79 * Rendez ce nouveau fichier de description exécutable, lancez-le. 84 80 85 81 Si tout se passe bien, vous devriez avoir un nouveau répertoire `caba` dans le répertoire courant. 86 La description SystemC de la ''top-cell'' est dans `caba/top.h.new`. DSX alloue automatiquement des adresses aux 87 segments mémoire pour lesquels les adresses de base ne sont pas imposées par l'utilisateur. 88 [[BR]] 89 [[Image(MjpegCourse:q.gif)]] Q2: '''''Visualisez le fichier de "top-cell" pour déterminer les adresses 90 et les tailles des 6 segments de l'espace adressable définis dans cette application.''''' 82 La description SystemC de la ''top-cell'' est dans `hard/top.cpp`. 91 83 92 84 = 2. Déploiement de l'application SplitMsg = … … 94 86 On va commencer par déployer l'application !SplitMsg, qui ne comporte que deux tâches et un canal 95 87 sur notre architecture de SoC monoprocesseur. 96 * Créez dans le répertoire TP2 un sous-répertoire 'splitmsg' (Important!)88 * Créez dans le répertoire TP2 un sous-répertoire 'splitmsg' 97 89 * Recopiez dans ce répertoire la description DSX de l'application !SplitMsg du TP1. 90 * Recopiez dans ce répertoire la description DSX de vgmn_noirq_mono 98 91 * Modifiez cette description DSX en ajoutant après la description du TGG l'instanciation de l'architecture matérielle !VgmnNoirqMono. 99 92 … … 109 102 from soclib import * 110 103 111 import sys112 sys.path.append("..")113 114 104 from vgmn_noirq_mono import VgmnNoirqMono 115 105 … … 122 112 123 113 Dans cette section, un objet `Mapper` doit être créé. 124 Supposons qu'on crée une variable `mapper`, l'architecture matérielle doit 125 être référencée à travers mapper.hard.''nom'' pour accéder aux composants 126 créés par self.''nom'' dans la description de la plateforme. 127 De même les objets logiciels doivent être accédés à travers mapper.tcg!['nom']. 114 Supposons qu'on crée une variable `mapper`, 115 les objets logiciels doivent être accédés à travers mapper.tcg!['nom']. 128 116 Il va falloir placer toutes les tâches, tous les canaux de communication, 129 117 tous les objets logiciels associés aux processeurs et enfin les objets globaux du système. … … 139 127 # mapping the "prod0" and "cons0" tasks 140 128 141 mapper.map("prod0", 142 run = mapper.hard.processor, 143 stack = mapper.hard.cram0, 144 desc = mapper.hard.cram0, 145 status = mapper.hard.uram0, 146 code = mapper.hard.cram0) 147 148 mapper.map("cons0", 149 run = mapper.hard.processor, 150 stack = mapper.hard.cram0, 151 desc = mapper.hard.cram0, 152 status = mapper.hard.uram0, 153 code = mapper.hard.cram0) 129 mapper.map(mapper.tcg["prod0"], 130 run = "processor", 131 stack = "cram0", 132 desc = "cram0", 133 status = "uram0") 134 135 mapper.map(mapper.tcg["cons0"], 136 run = "processor", 137 stack = "cram0", 138 desc = "cram0", 139 status = "uram0") 154 140 155 141 # mapping the MWMR channel 156 142 157 mapper.map( "fifo", 158 lock = mapper.hard.locks, 159 status = mapper.hard.cram1, 160 desc = mapper.hard.cram1) 143 mapper.map( mapper.tcg["fifo"], 144 status = "cram1", 145 desc = "cram1") 161 146 162 147 # mapping the software objects associated to a processor 163 148 164 mapper.map( "processor",165 desc = mapper.hard.cram0,166 priv = mapper.hard.cram0,167 status = mapper.hard.uram0)149 mapper.map( mapper.platform["processor"], 150 desc = "cram0", 151 priv = "cram0", 152 status = "uram0") 168 153 169 154 # mapping the software objects used by the embedded OS 170 155 171 156 mapper.map(mapper.tcg, 172 desc = mapper.hard.cram1,173 shared = mapper.hard.uram1,174 code = mapper.hard.cram1)157 desc = "cram1", 158 shared = "uram1", 159 code = "cram1") 175 160 }}} 176 161 … … 185 170 # SystemC simulator for the hardware architecture at Cycle Accurate/Bit Accurate abstraction level 186 171 187 muteks = MutekS() 188 simulator = Caba() 189 mapper.generate( muteks, simulator ) 172 mapper.generate( MutekS() ) 190 173 191 174 # The software application for a POSX workstation can still be generated … … 194 177 tcg.generate(posix) 195 178 196 # Global Makefile generation 197 TopMakefile( muteks, simulator, posix ) 198 }}} 199 200 201 [[Image(MjpegCourse:q.gif)]] Q3: '''''Quels objets logiciels doit-on placer dans 179 }}} 180 181 182 [[Image(MjpegCourse:q.gif)]] Q2: '''''Quels objets logiciels doit-on placer dans 202 183 l'espace addressable pour une tâche ? pour un canal mwmr ? pour un processeur ?''''' 203 184 … … 206 187 $ ./SplitMsg.py 207 188 }}} 208 * Générez le code binaire et le modèle SystemC de l'architecture matérielle.209 {{{210 $ make211 }}}212 213 Une fois la compilation effectuée, visualisez le fichier de "top cell" généré par DSX spécifiquement pour214 ce déploiement. Il se situe dans muteks/caba/top.h. Déterminez les adresses215 et les tailles des 6 segments de l'espace adressable définis dans cette application.[[BR]]216 [[Image(MjpegCourse:q.gif)]] Q4: '''''En quoi diffèrent-ils de ces mêmes segments217 vus à la question 2 ?'''''218 189 219 190 * Executez l'application logicielle sur la station de travail … … 223 194 * Simulez l'exécution de l'application logicielle sur le modèle SystemC du SoC 224 195 {{{ 225 $ ./exe.muteks_ caba226 }}} 227 228 [[Image(MjpegCourse:q.gif)]] Q 5: '''''Qu'observez-vous ? En quoi est-ce différent de ce196 $ ./exe.muteks_hard 197 }}} 198 199 [[Image(MjpegCourse:q.gif)]] Q2: '''''Qu'observez-vous ? En quoi est-ce différent de ce 229 200 qui se passe dans la version pour station de travail ?''''' 230 201 … … 253 224 {{{from soclib import *}}} doit être présente avant la description des tâches dans 254 225 votre fichier de description. 255 * Pour la tâche `tg`, ajoutez un deuxième élément dans la liste des implémentations disponibles: 256 {{{ 257 tg = TaskModel( 'tg', 258 outfifos = [ 'output' ], 259 impl = [ SwTask( 'tg', 260 stack_size = 1024, 261 sources = [ 'src/tg.c' ], 262 defines = [ 'FILE_NAME' ] ), 263 HwTask( Tg ) 264 ] ) 265 }}} 266 * De même, pour la tâche `ramdac`, ajoutez l'implémentation suivante: 267 {{{ 268 HwTask( Ramdac ) 226 * Pour la tâche `tg`, modifiez la déclaration de la tâche pour ajouter l'implémentation matérielle: 227 {{{ 228 from soclib.hwtask import HwTask, MwmrCoproc 229 230 hw_fifo_tg = MwmrCoproc( 231 module = 'caba:fifo_reader', 232 from_coproc = [ 'output:fifo' ], 233 to_coproc = [], 234 config = [], 235 status = [], 236 binary = 'bash', 237 argv = [ 'bash', '-c', 'while cat %(FILE_NAME)s ; do true ; done' ], 238 word_t = 'uint32_t' ) 239 240 TaskModel( 241 'tg', 242 ports = {'output':MwmrOutput(32)}, 243 impl = [ SwTask( 'tg', 244 bootstrap = 'bootstrap', 245 stack_size = 4096, 246 sources = [ 'tg.c' ], 247 defines = [ 'FILE_NAME' ] ), 248 HwTask( hw_fifo_tg ), 249 ] ) 250 }}} 251 * De même, pour la tâche `ramdac`: 252 {{{ 253 from soclib.hwtask import HwTask, MwmrCoproc 254 255 hw_fifo_ramdac = MwmrCoproc( 256 module = 'caba:fifo_writer', 257 from_coproc = [], 258 to_coproc = [ 'input:fifo' ], 259 config = [], 260 status = [], 261 binary = 'soclib-pipe2fb', 262 argv = [ 'soclib-pipe2fb', '%(WIDTH)s', '%(HEIGHT)s' ], 263 word_t = 'uint32_t' ) 264 265 TaskModel( 266 'ramdac', 267 ports = {'input':MwmrInput(48*8)}, 268 impl = [ SwTask( 'ramdac', 269 bootstrap = 'bootstrap', 270 stack_size = 4096, 271 sources = [ 'ramdac.c', 'ramdac_x11.c' ], 272 defines = [ 'WIDTH', 'HEIGHT' ] ), 273 HwTask( hw_fifo_ramdac ) 274 ] ) 269 275 }}} 270 276 … … 273 279 * Les coprocesseurs `tg` et `ramdac` sont spécifiques, ils doivent 274 280 faire l'objet d'un déploiement non pas en tant que tâches logicielles sur un processeur, mais 275 en tant que coprocesseurs rattachés par un contrôleur MWMR à un interconnect VCI . Le déploiement276 valide pour `tg` est par exemple:281 en tant que coprocesseurs rattachés par un contrôleur MWMR à un interconnect VCI, et 282 assignés à une adresse. Un déploiement valide pour `tg` est par exemple: 277 283 {{{ 278 284 mapper.map( 'tg0', 279 vci = mapper.hard.vgmn ) 285 vci = 'vgmn0', 286 addr = 0x94000000 ) 280 287 }}} 281 288 * De même déployez `ramdac` sur la plateforme. 282 * Relancez la description, recompilez, lancez la simulation. Ajoutez le flag `-e` sur la ligne de commande 283 pour que la simulation ne soit pas limitée au premier million de cycles. 289 * Relancez la description, recompilez, lancez la simulation. 284 290 {{{ 285 291 $ ./description 286 $ make 287 $ ./exe.muteks_caba -e 292 $ ./exe.muteks_hard 288 293 }}} 289 294 … … 298 303 L'environnement DSX permet actuellement d'utiliser deux systèmes d'exploitation embarqués. 299 304 300 * Mutek/S, un micro-noyau "statique" , très performant, mais ne fournissant pas la compatibilité POSIX. En particulier, il ne permet pas la création dynamique de tâches au moment de l'exécution.301 * Mutek/ D, un micro-noyau fournissant aux applications l'API des threads POSIX (y compris la création dynamique de tâches).305 * Mutek/S, un noyau "statique" , très performant, mais ne fournissant pas la compatibilité POSIX. En particulier, il ne permet pas la création dynamique de tâches au moment de l'exécution. 306 * Mutek/H, un noyau fournissant aux applications l'API des threads POSIX (y compris la création dynamique de tâches). 302 307 303 308 Modifiez la description DSX de l'application MJPEG, pour utiliser l'OS Mutek/D. La section D devient: 304 309 {{{ 305 muteks = MutekS() 306 simulator_s = Caba() 307 mapper.generate( muteks, simulator_s ) 308 309 mutekd = MutekD() 310 simulator_d = Caba() 311 mapper.generate( mutekd, simulator_d ) 312 313 posix = Posix() 314 tcg.generate(posix) 315 316 TopMakefile( muteks, simulator_s, mutekd, simulator_d, posix ) 317 }}} 318 319 Il faut définir deux simulateurs différents (simulator_s et simulator_d) suivant qu'on utilise MUTEK/S ou MUTEK/D, 320 car DSX calcule automatiquement la capacité des deux bancs mémoire physique en fonction des la taille des différents 321 objets logiciels à ranger en mémoire. Le code généré pour MUTEK/S étant beaucoup plus compact, on a des mémoires 322 plus petites dans le cas de MUTEK/S. 323 324 (Notez le changement dans la `TopMakefile`) 325 326 * Relancez la description, recompilez, lancez la simulation du SoC avec Mutek/D 310 mapper.generate( 'muteks' ) 311 mapper.generate( 'mutekh' ) 312 tcg.generate('posix') 313 }}} 314 315 * Relancez la description, recompilez, lancez la simulation du SoC avec Mutek/H 327 316 (attention, il y a deux simulateurs avec des noms différents) 328 317 {{{ 329 318 $ ./description 330 $ make 331 $ ./exe.mutekd_caba -e 319 $ ./exe.mutekh_hard 332 320 }}} 333 321 334 322 [[Image(MjpegCourse:q.gif)]] Q8: '''''Combien de cyles faut-il pour décompresser 25 images avec MUTEK/D? Comment expliquer ce résultat?''''' 335 323 336 [[Image(MjpegCourse:q.gif)]] Q9: '''''En consultant la description SystemC de l'architecture matérielle générée par DSX, déterminez la capacité mémoire des deux bancs mémoire RAM0 et RAM1 suivant qu'on utilise MUTEK/S ou MUTEK/D.''''' 324 [[Image(MjpegCourse:q.gif)]] Q9: '''''En consultant les headers de l'objet binaire généré, déterminez la capacité mémoire des deux bancs mémoire RAM0 et RAM1 suivant qu'on utilise MUTEK/S ou MUTEK/H.''''' 325 326 {{{ 327 $ mipsel-unknown-elf-objdump -h bin.muteks 328 $ mipsel-unknown-elf-objdump -h bin.mutekh 329 }}} 337 330 338 331 = 5. Compte-rendu = … … 345 338 tp2/splitmsg/ 346 339 tp2/splitmsg/producer.c 340 tp2/splitmsg/producer.task 347 341 tp2/splitmsg/consumer.c 342 tp2/splitmsg/consumer.task 348 343 tp2/splitmsg/splitmsg.py 349 344 tp2/mjpeg/mjpeg.py 350 345 tp2/mjpeg/src/ 351 tp2/mjpeg/src/iqzz.c 352 tp2/mjpeg/src/libu.c 353 }}} 354 355 * Les fichiers `splitmsg.py` et `mjpeg.py` seront complets, avec vos descriptions de tâches et le mapping. 346 tp2/mjpeg/src/iqzz/ 347 tp2/mjpeg/src/iqzz/iqzz.c 348 tp2/mjpeg/src/iqzz/iqzz.task 349 tp2/mjpeg/src/libu/ 350 tp2/mjpeg/src/libu/libu.c 351 tp2/mjpeg/src/libu/libu.task 352 }}} 353 354 * Les fichiers `splitmsg.py` et `mjpeg.py` seront complets, avec vos descriptions de TCG et le mapping. 356 355 Pour mjpeg, il y aura les directives de génération de code pour Mutek/S et Mutek/D. 357 356 * Le répertoire `mjpeg/src` contiendra uniquement les implémentation de vos deux tâches libu et iqzz … … 360 359 posées dans le texte, nommé `tp2/rapport.pdf`. 361 360 362 Vous livrerez cette archive avant mardi 2 0 fevrier 2007, 18h00 à [MailAsim:nipo Nicolas Pouillon].361 Vous livrerez cette archive avant mardi 26 fevrier 2008, 18h00 à [MailAsim:nipo Nicolas Pouillon]. 363 362 364 363 = Suite =