Hallo Gemeinde, ich spiele seit einigen Wochen mit den STM32F10x herum. Jetzt habe ich mir zur Aufgabe gemacht, einen VCP über USB zu realisieren. Mit dem Ergebnis das ich das nicht alleine hinbekomme. Vielleicht hat hier jemand, der bereits Erfahrungen mit der USB Lib gesammelt hat, die Zeit und Lust mir auf die Sprünge zu helfen ? Ich würde mich freuen, wenn wir konstruktiv eine Lösung erarbeiten können. Dann kommen wir hier auch einmal von den ganzen Grundsatzdiskussionen weg und schaffen für Einsteiger wie mich, Infos im Netz. Mir geht es nicht um ein fertiges Beispiel, eher darum zu verstehen was passiert. Zur Ausgangssituation: Entwicklungsumgebung ist Coocox. Hardware ein Reusch mit einem STM32F103RGT6 http://re.reworld.eu/de/produkte/s64dil-103/right.htm Den Artikel kenne ich http://www.mikrocontroller.net/articles/STM32_USB-FS-Device_Lib Dort habe ich mir unter entsprechendem Link die STM32_USB-FS-Device_Lib_V4.0.0 herunter geladen. Die Hardware Läuft soweit. Ich habe ein Blink Demo geschrieben und mit STM Link V2 geflasht. Windwos erkennt bei entsprechender Beschaltung auch eine Hardware. Das VirtualComport_Loopback Example scheint mir am sinnvollsten für mein Vorhaben. Angehangen habe ich die USB_Lib_Hierarchy Ein einfaches Anhängen der Lib Files sorgt nach dem Compile dafür, dass die hw_config.h fehlt. Im nächsten Schritt habe ich die hw_config.h/c ins Projekt eingefügt. Hier wird die platform_config.h includiert. Dann werden einige Fehler geschmissen. Ab hier hört mein Verständnis auf. Es läuft wohl darauf Hinaus die platform_config.h auf meinen Controller anzupassen. Ich habe mal das Projekt angefügt. Um manchen Bemerkungen vorzubeugen: Ja, ich bin kein C und Mikrocontroller Profi - habe aber Spaß daran etwas dazu zu lernen ;) Gruß Ernst
Dann schau mal da: "http://www.mikrocontroller.net/attachment/203918/USB-CDC-STM32F103.zip" Du könntest es direkt so wie es ist benutzen, aber auch wenn du es anders machen willst, hast du damit wenigstens ein Beispiel zum Lesen. W.S.
Danke! Auf den ersten Blick übersichtlicher als gefühlte 20 h und 10 c files. Setze ich mich gleich mal dran! Ernst
Hallo, du schreibst im Kommentar zur Funktion word UsbSetup (void) /************ USB-Setup **********************************/ /* Die Pins müssen bereits richtig gesetzt sein */ /* ebenso Clock ein und Powerdown aus. */ /* Interrupt 20 ist USB-IRQ (USB_LP_CAN1_RX0_IRQHandler) */ /**********************************************************/ Ich habe meine main.c folgendermaßen aufgebaut:
1 | int main(void) |
2 | {
|
3 | GPIO_InitTypeDef GPIO_InitStructure; |
4 | |
5 | SystemInit(); |
6 | |
7 | RCC_APB1PeriphClockCmd(RCC_APB1Periph_USB,ENABLE); |
8 | |
9 | // PA11 = USBDM, PA12 = USBDP
|
10 | RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); |
11 | GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; |
12 | GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; |
13 | GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11 | GPIO_Pin_12; |
14 | |
15 | GPIO_Init(GPIOA, &GPIO_InitStructure); |
16 | |
17 | UsbSetup(); |
18 | |
19 | |
20 | while(1){} |
21 | |
22 | }
|
Das verfluchte Teil wird aber im Gerätemanager als unknown deviece angezeit :(
Den Takt vom USB habe ich auch mal aktiviert, ohne Erfolg
1 | RCC_APB1PeriphClockCmd(RCC_APB1Periph_USB,ENABLE); |
Das heißt, dass sich USB überhaupt nicht am PC angemeldet hat. Weißt Du wie die USB Anmeldeprozedur funktioniert? Wird der USB Interrupt überhaupt angesprungen? Eine Sache geht schon mal: Der Pull-Up Winderstand von 1,5K an D+ funktioniert.
:
Bearbeitet durch User
Markus Müller schrieb: > Eine Sache geht schon mal: Der Pull-Up Winderstand von 1,5K an D+ > funktioniert. Jo, da ist ne Transistorschaltung vorgesehen. Ich ziehe den Pin auf Masse (siehe Schaltplan vom verwendeten Board). > Weißt Du wie die USB Anmeldeprozedur funktioniert? > Wird der USB Interrupt überhaupt angesprungen? Laut Debugger wird der Interrupt nicht angesprungen. Ich weiß nicht wie die Anmeldeprozedur funktioniert. Ernst
Der Interrupt MUSS angesprungen werden. Solange das nicht geht braucht Dich die USB Anmeldeprozedur nicht interessieren (die nennt man "Enumeration"). Somit gilt: - HW Überprüfen, D+ und D+ gehen direkt zur CPU? - An D+ darf nur ein Pull-Up Widerstand von 1K5 an +5V oder +3,3V sein Als nächstes SW überprüfen, am besten mit dem Debugger durchsteppen, da müssen die Punkte auftauchen: - Clock's für CPU und USB initialisieren - Clock Teiler für USB richtig eingestellt (48MHz) - Aktivierung der Peripherie-Clocks für GPIOA und USB - Initialisierung Port-Pins - Initialisierung Pot-Pins auf Alternative Funktion - Initialisierung USB Core - Initialisierung Endpoints - Initialisierung NVIC für USB Ich glaube das war's Wenn dann der Debugger im USB Interrupt hängen bleibt, dann ist erst mal gut, bzw. der erste Schritt geschafft.
:
Bearbeitet durch User
Markus Müller schrieb: > Somit gilt: > - HW Überprüfen, D+ und D+ gehen direkt zur CPU? > - An D+ darf nur ein Pull-Up Widerstand von 1K5 an +5V oder +3,3V sein > > Als nächstes SW überprüfen, am besten mit dem Debugger durchsteppen, da > müssen die Punkte auftauchen: > - Clock's für CPU und USB initialisieren > - Clock Teiler für USB richtig eingestellt (48MHz) > - Aktivierung der Peripherie-Clocks für GPIOA und USB > - Initialisierung Port-Pins > - Initialisierung Pot-Pins auf Alternative Funktion > - Initialisierung USB Core > - Initialisierung Endpoints > - Initialisierung NVIC für USB > Danke! Die Hardware kann man erst einmal ausschließen. Ich nutze folgende Hardware: http://re.reworld.eu/de/produkte/s64dil-103/right.htm Auf den ersten Blick fällt mir der Clock Teiler der CPU auf. Der szteht noch auf 72MHz. Ich gehe deine Liste morgen mal durch. Gruß
Die CPU darf auch mit 72MHz laufen, dann muss der Clock Teiler für USB auf 1.5 eingestellt sein.
Im Register RCC CFGR das Bit USBPRE Beim STM32F103 muss der Core mit 48MHz oder 72MHz laufen wenn man USB benutzen möchte. Beim STM32F2xx oder STM32F4xx ist das entspannter da alles über die USB PLL läuft.
:
Bearbeitet durch User
>Ich nutze folgende Hardware: >http://re.reworld.eu/de/produkte/s64dil-103/right.htm Wieso fragst du da nicht einfach mal nach einem Beispiel?
Markus Müller schrieb: > a) Clock's für CPU und USB initialisieren > b) Clock Teiler für USB richtig eingestellt (48MHz) > c) Aktivierung der Peripherie-Clocks für GPIOA und USB > d) Initialisierung Port-Pins > e) Initialisierung Pot-Pins auf Alternative Funktion > f) Initialisierung USB Core > g) Initialisierung Endpoints > h) Initialisierung NVIC für USB Hier mal meine main.c
1 | int main(void) |
2 | {
|
3 | GPIO_InitTypeDef GPIO_InitStructure; |
4 | |
5 | SystemInit(); //im header 48MHz |
6 | |
7 | RCC_APB1PeriphResetCmd(RCC_APB1Periph_PWR, ENABLE); |
8 | RCC_APB1PeriphClockCmd(RCC_APB1Periph_USB,ENABLE); |
9 | |
10 | RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); |
11 | GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; |
12 | GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; |
13 | GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11 | GPIO_Pin_12; |
14 | |
15 | GPIO_Init(GPIOA, &GPIO_InitStructure); |
16 | |
17 | UsbSetup(); |
18 | |
19 | while(1) |
20 | {
|
21 | }
|
22 | }
|
So läuft es immer noch nicht. Was ich in der Lib vermisse, ist die NVIC initialisierung für USB. Sonst kann ich alle Punkte abhaken. @W.S. vielleicht magst du dich nochmal äussern? Anbei auch mein Coocox Projekt. Die letzten wurden ja 1000 mal heruntergeladen ;) Gruß Ernst
__irq_USB_LP_CAN1_RX0_IRQHandler() wird nirgends aufgerufen. Die Funktion ist einfach nur da. Nun muss die aus dem ISR Handler noch aufgerufen werden.
Markus Müller schrieb: > __irq_USB_LP_CAN1_RX0_IRQHandler() Das ist der zuständige Interrupt-Handler, jedenfalls beim STM32F103ZET6. Also hier nochmal die Liste der Prerequisites: - richtigen USB-Takt einstellen, sonst geht die SIE nicht. - Alle Pins für den USB richtig einstellen, nicht nur D+ und D-, sondern auch für VBUS und den Aktivator (1k5 an D+) - wo letzterer bei DIR liegt und wie herum er geht, mußt du selber sehen. - sicherheitshalber im Startupcode nachschauen, ob der dort als [weak] gezeichnete Dummy-Handler für den Interrupt 20 vielleicht bei dir anders heißt. Und aus dem .h die .inf Datei herauskopieren und verwenden. Das Teil meldet sich mit VID 0x416 und PID 0x5011 an, also als ein Realtek device. W.S.
Hi, die CPU wird mit 48MHz getaktet, der USB ohne Vorteiler 1.5. VBUS ist doch die 5V Versorgung!? Mein Board wird vom USB versorgt. Den "Aktivator" lege ich im Moment von Hand auf, also D+ über 1k5 auf +5V. Verstehe ich richtig das also D+, D- und der Pull Up an D+ beschaltet sein müssen? Aus welcher Doku lese ich genau heraus ob der Dummy Handler für den Interrupt 20 beim F103RGT6 genauso heißt. Gruß und Danke!
OK, bei mir wird die CPU deutlich schneller getaktet. Da mußt du dich mit dem ReferenzManual befassen, um die korrekte Einstellung des USB-Taktes für deinen Anwendungsfall nachzulesen. Der Aktivator kann im prinzip auch statisch sein, Hauptsache, daß er den D+ nach oben zieht, sobald du mit deinen sonstigen Setup's fertig bist. Ach ja, schau in die Quelle, bei mir liegt er auf Port B: PB2, das ist bei dir vermutlich anders. D+ und D- müssen natürlich zur USB-Buchse gehen, logo. Bei mir sind da noch jeweils 33 Ohm in der Leitung. Und VBUS liegt m.W. auf Port G: PG15 Die ganzen Dummy-IR-Handler-Adressen siehst du im Startupcode. Dort sollte sowas stehen: DCD USB_LP_CAN1_RX0_IRQHandler ; USB Low Priority or CAN1 RX0 und EXPORT USB_LP_CAN1_RX0_IRQHandler [WEAK] W.S.
>__irq_USB_LP_CAN1_RX0_IRQHandler() >Das ist der zuständige Interrupt-Handler, Bei Keil vermutlich. Aber nicht bei seinem Startup File. >Aus welcher Doku lese ich genau heraus ob der Dummy Handler für den >Interrupt 20 beim F103RGT6 genauso heißt. Wie der Handler wirklich heisst findest du in deiner Startup Datei. Und siehe da er heisst so: void USB_LP_CAN1_RX0_IRQHandler(void)
holger schrieb: > findest du in deiner > Startup Datei. Und siehe da er heisst so: > void USB_LP_CAN1_RX0_IRQHandler(void) Schreib keinen solchen Unsinn. Die Startupdatei ist Assembler und kein C, also nix mit void... ernst schrieb: > die CPU wird mit 48MHz getaktet, der USB ohne Vorteiler 1.5. Da habe ich das deutliche Gefühl, daß der Knackpunkt bei dir die Taktfrequenz für den USB Core ist. Du mußt es so hinkriegen, daß dort 48 MHz ankommen. W.S.
>> findest du in deiner >> Startup Datei. Und siehe da er heisst so: >> void USB_LP_CAN1_RX0_IRQHandler(void) > >Schreib keinen solchen Unsinn. Die Startupdatei ist Assembler und kein >C, also nix mit void... Die Startupdatei in seinem ZIP ist in C geschrieben. Vieleicht einfach mal selber nachsehen oder ansonsten die Fresse halten?
Holger Krähenbühl schrieb: > Wie gings hier weiter? Es haben sich mal ausnahmsweise alle an die Empfehlung gehalten: "Vieleicht einfach mal selber nachsehen oder ansonsten die Fresse halten?" :)
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.