kategorie:

menu:


Kompilace programů pro IBM Cell (PS3)

15.05.2010   ::    topic: Programování

Součástí předmětu Speciální architektury (X36SPA) je úloha jejímž cílem je napsat program pro architekturu IBM Cell. Tento program by měl využívat SPE jednotky k urychlení výpočtu. K testování úlohy je na FELu k dispozici výpočetní cluster sestavený z konzolí Sony PS3. Protože příprava vývojového prostředí, tak jak je doporučována na cvičeních předmětu, je poměrně komplikovaná a již první týden odradila většinu studentů, popíši zde schůdný postup jak dotáhnout úlohu ke zdárnému výsledku. Snad tento krátký návod někomu v příštích letech pomůže.

Postup popisovaný na stránkách předmětu vyžaduje instalaci zastaralé Fedory 9 (32bit), Eclipse IDE a IBM Cell SDK (vyžaduje registraci). Pokud se nebudete držet přesně této kombinace, pravděpodobně dříve či později narazíte na neřešitelný problém. Ale i pokud se v Linuxu orientujete a nenastanou během celého procesu žádné komplikace, je instalace (ať už na disk, nebo do virtuálního stroje) práce téměř na celé odpoledne s nejistým výsledkem. Všichni (čtyři) co jsme předmět nevzdali jsme se shodli na tom že rozfungovat vývojové prostředí pro Cell je jednou z nejhorších částí předmětu SPA. Proto mám následující radu: vykašlete se na instalaci Cell SDK a Eclipse…

Mnohem schůdnější cestou je kompilace programu přímo na cílovém stroji (ssh) s ručně napsaným Makefile a použití libovolného editoru na psaní kódu. Postup kompilace programu obsahující kód spustitelný na SPE jednotkách je nejlépe pochopitelný z následujícího diagramu:

Cell compile diagram
zdroj: kernel.org – Cell programming tutorial

Samotný Makefile který celou tuto zběsilost provede může pak vypadat nějak takto:

BIN=binarka
TEST_ARGS=

PPU_OBJS=main.o ppu-spucode.o
PPU_CARGS=-I/opt/cell/sdk/usr/include 
  -O0 -m32 -g3 -c -fmessage-length=0 -fno-inline 
  -mabi=altivec -maltivec -MMD -MP
PPU_LARGS= -m32 -lorte -lopal
LIBS= -lpthread -lspe2

SPU_OBJS= spucode.o
SPU_CARGS=-O0 -g3 -c -fmessage-length=0 -fno-inline 
  -mtune=cell -mfloat=fast -mdouble=fast -Wno-main -march=cell -mea32 -MMD -MP
SPU_LARGS =

pgcc=ppu-gcc
sgcc=spu-gcc

all: $(PPU_OBJS) 
  $(pgcc) $(PPU_LARGS) $(LIBS) $(OBJ) -o $(BIN)

test: all
  @echo
  @echo
  ./$(BIN) $(TEST_ARGS)

clean:
  rm $(PPU_OBJS) $(SPU_OBJS) $(BIN) spucode

valgrind: clean all
  valgrind --leak-check=full  --show-reachable=yes ./$(BIN) $(TEST_ARGS)


main.o: main.c main.h
  $(pgcc)  $(PPU_CARGS) -c main.cpp

## convert spu executable to ppu object
ppu-spucode.o: spucode
  ppu-embedspu -m32 spucode spucode ppu-spucode.o
  ppu-ar -qcs spu_code_lib.a ppu-spucode.o

## make spu executable
spucode: $(SPU_OBJS)
  $(sgcc)  $(SPU_OBJS) $(SPU_LARGS) -o spucode 

# make spu object
spucode.o: spucode.c spucode.h
  $(sgcc) $(SPU_CARGS) -o spucode.o  spucode.c

Rada na závěr

Mějte na paměti že SPE obsahuje pouhých cca 250KB paměti do kterých je potřeba vmáčknout jak kód tak data. Pokud se budete pokoušet psát kód pro SPE v C++ s použitím STL knihovny, s největší pravděpodobností dojedete na chybovou hlášku .text exceeds local store range. Proto je vhodné hned od začátku psát tuto část algoritmu čistě v C.

Jako odrazový můstek pro experimenty se vám může hodit série o Cell na Root.cz nebo můj jednoduchý příklad (i s Makefile) vycházející ze vzorové úlohy na SPA (nepřehledný zdroják).