Arduino Pro Mini 5V und SD Card Reader funktioniert nicht

Guten Morgen,

es gibt zu diesem Thema einen 4 Jahre alten Thread:

http://forum.arduino.cc/index.php?topic=277464.0

Aber dieser hilft mir nicht weiter.

Versuchsaufbau:

Arduino Pro Mini 5V
0.96 Display (80x160)
SD-Card Reader

Der Aufbau funktioniert mit einem Arduino Nano einwandfrei!

Der identische Sketch auf einem Pro Mini funktioniert nicht.

  • Pro Mini und das Display funktionieren (mit einem anderen Sketch ohne SD-Card-Zugriff)
  • Nur der SD-Card Reader funktioniert nicht.

Das Thema des alten Threads mit den Signalpegeln würde ich aber ausschließen, da meine SD Reader offensichtlich einen Level Shifter verbaut haben:

https://www.aliexpress.com/item/Micro-SD-card-mini-TF-card-reader-module-SPI-interfaces-with-level-converter-chip-for-arduino/32424558182.html?spm=a2g0s.9042311.0.0.4f8f4c4dNbuaOM

Danke für sachdienliche Hinweise!

Der Levelshifter dürfte für den Betrieb an 5V-Arduinos gedacht sein. SD arbeiten im Normalfall mit 2,7-3,6V

Gruß Tommy

Zu wenig Information!

Code geheim.
Beschaltung geheim.

0.96 Display (80x160)

Ein SPI Display?

SD-Card Reader

Der hat einen Fehler, funktioniert nicht im Verbund mit weiteren SPI Slave Geräten.
Kann man aber modifizieren/reparieren.

Der Aufbau funktioniert mit einem Arduino Nano einwandfrei!

Der identische Sketch auf einem Pro Mini funktioniert nicht.

  • Pro Mini und das Display funktionieren (mit einem anderen Sketch ohne SD-Card-Zugriff)
  • Nur der SD-Card Reader funktioniert nicht.

Kann ich nicht glauben.
Welche Fehlermeldungen bekommst Du. Gib uns mal einen genaue Fehlerbeschreibung. "Geht nicht" ist zuwenig.
Zeig uns gute Fotos vom Aufbau mit NANO und MINI.

Grüße Uwe

Hallo,

zuerst mal vielen Dank für Eure Beiträge.

Hiermit nachgereicht weitere Details:

Die Displays sind SPI Displays mit ST7735 Chip.

https://www.aliexpress.com/item/IPS-0-96-inch-7P-SPI-HD-65K-Full-Color-LCD-Module-ST7735-Drive-IC-80/32906520459.html?spm=a2g0s.9042311.0.0.52074c4ddjs3Mf

Aufgebaut habe ich zuerst mit einem Arduino Nano (China Clone mit CH340 Treiber)

  • Adafruit ST77xx Libr
  • Adafruit GFX Lib
  • Arduino SD Lib

Aufbau nach Adafruit Tutorial (ich bin kein Experte) und Adafruit Example Sketch.

Display CS auf Pin7
SD-Card CS auf Pin4
Alle anderen Pins nach Standardvorgaben.

Mit dem Nano hat dieser Aufbau funktioniert, den Sketch habe ich dann für eine Slide Show modifiziert. Hat wunderbar geklappt, auch mit einem gelöteten Aufbau.

Nun wollte ich diese Lösung auf einen Pro Mini aufbauen, da sich mit diesem ein wesentlich kompakterer Aufbau für eine Modellbauanwendung realisieren lässt.

Die Fehlermeldung der SD Karte im Serial Monitor ist die klassische
SD Card initialization - failed
Dann natürlich die xxx.bmp not found Meldungen

Die Fotos vom Aufbau kann ich nachreichen, wenn ich diese am Breadboard wieder gesteckt habe.

Vielversprechend erscheint mir der Hinweis mit dem Konstruktions-Fehler des SD-Card Modules , ich werde dieser Sache nachgehen. Bei einem Stückpreis von 50 US-Cent kann ich schon mal auch ein Modul beim Löten schrotten :wink:

Hast Du auch den Satz im verlinkten Beitrag gelesen, dass das Modul nur mit 5V funktioniert?

Gruß Tommy

Hallo Tommy,

der Pro Mini 5V hat ja nur 5 Volt.... :wink:
Am Nano funktioniert es einwandfrei ... an 5V

Den gibt es aber auch in einer 3,3V-Variante.

Gruß Tommy

Tommy56:
Den gibt es aber auch in einer 3,3V-Variante.

Gruß Tommy

Hallo Tommy,

ich weiß. Darum habe ich auch in der Überschrift 5V dazu geschrieben.

Liebe Grüße
Peter

Sorry, überlesen.

Gruß Tommy

Display CS auf Pin7
SD-Card CS auf Pin4

Ist das Programm wirklich so geheim, dass das alles in Prosa kommen muss?

Naja, wenn das so geheim sein muss, dann behalte ich auch für mich, dass Pin 10 (SS) ein Output sein muss, oder zumindest High, damit SPI im Master Modus laufen kann,
Nein, davon erzähle ich dir dann nichts!

Hallo combie,

Code ist nicht geheim, ich war nur heute den ganzen Tag nicht in der Bastelstube. Was hat es mit dem Pin10 auf sich und warum benötigt der Nano diesen nicht?

Liebe Grüße
Peter

Hier der Code (nicht lachen, nur schnell zusammengefpriemelt für den Test)

Hier auch gleich noch ein Tipp, falls jemand diese Displays verwenden möchte.
Mit dem Sketch aus der Adafruit Vorlage werden bei diesen Displays die Farben Rot und Blau vertauscht. Ich habe dies wie folgt korrigiert:

//tft.pushColor(tft.color565(r,g,b)); original
tft.pushColor(tft.color565(b,g,r)); // corrected

Und hier mein gesamter Sketch:

...

#include <Adafruit_GFX.h>    // Core graphics library
#include <Adafruit_ST7735.h> // Hardware-specific library for ST7735
//#include <Adafruit_ST7789.h> // Hardware-specific library for ST7789
#include <SPI.h>
#include <SD.h>

// TFT display and SD card will share the hardware SPI interface.
// Hardware SPI pins are specific to the Arduino board type and
// cannot be remapped to alternate pins.  For Arduino Uno,
// Duemilanove, etc., pin 11 = MOSI, pin 12 = MISO, pin 13 = SCK.

#define SD_CS  4  // Chip select line for SD card
#define TFT_CS   9  // Chip select line for TFT display
#define TFT_DC   8  // Data/command line for TFT
#define TFT_RST  7  // Reset line for TFT (or see below...)
//Use this reset pin for the shield!
// #define TFT_RST  -1  // you can also connect this to the Arduino reset!
...
void setup(void) {
  Serial.begin(9600);

  while (!Serial) {
    delay(10);  // wait for serial console
  }

  pinMode(TFT_CS, OUTPUT);
  digitalWrite(TFT_CS, HIGH);
  pinMode(SD_CS, OUTPUT);
  digitalWrite(SD_CS, HIGH);

  ...

  // Use this initializer (uncomment) if you're using a 0.96" 180x60 TFT
 tft.initR(INITR_MINI160x80);   // initialize a ST7735S chip, mini display

...

  Serial.print("Initializing SD card...");
  if (!SD.begin(SD_CS)) {
    Serial.println("failed!");
    return;
  }
  Serial.println("OK!");

  File root = SD.open("/");
  printDirectory(root, 0);
  root.close();
  
...
  
}

void loop() {
tft.setRotation(1); 
/* tft.fillScreen(ST7735_BLACK); // Clear display
    //  for(uint8_t i=0; i<4; i++)    // Draw 4 parrots
    //  bmpDraw("bmp1.bmp", tft.width() / 4 * i, tft.height() / 4 * i);
    // tft.setRotation(tft.getRotation() + 1); // Inc rotation 90 degrees
    // Bildausgabe */
    /*    bmpDraw("bmp1.bmp", 0, 0);
  delay(5000);
    tft.fillScreen(ST7735_BLACK); // Clear display
    delay (200);
    bmpDraw("bmp2.bmp", 0, 0);
  ... 

    tft.fillScreen(ST7735_BLACK); // Clear display
  
..

// #define BUFFPIXEL 20 Originl
#define BUFFPIXEL 30 // Test

void bmpDraw(char *filename, uint8_t x, uint16_t y) {

  File     bmpFile;
  int      bmpWidth, bmpHeight;   // W+H in pixels
  uint8_t  bmpDepth;              // Bit depth (currently must be 24)
  uint32_t bmpImageoffset;        // Start of image data in file
  uint32_t rowSize;               // Not always = bmpWidth; may have padding
  uint8_t  sdbuffer[3*BUFFPIXEL]; // pixel buffer (R+G+B per pixel)
  uint8_t  buffidx = sizeof(sdbuffer); // Current position in sdbuffer
  boolean  goodBmp = false;       // Set to true on valid header parse
  boolean  flip    = true;        // BMP is stored bottom-to-top
  int      w, h, row, col;
  uint8_t  r, g, b;
  uint32_t pos = 0, startTime = millis();

  if((x >= tft.width()) || (y >= tft.height())) return;

  Serial.println();
  Serial.print(F("Loading image '"));
  Serial.print(filename);
  Serial.println('\'');

  // Open requested file on SD card
  if ((bmpFile = SD.open(filename)) == NULL) {
    Serial.print(F("File not found"));
    return;
  }

  // Parse BMP header
  if(read16(bmpFile) == 0x4D42) { // BMP signature
    Serial.print(F("File size: ")); Serial.println(read32(bmpFile));
    (void)read32(bmpFile); // Read & ignore creator bytes
    bmpImageoffset = read32(bmpFile); // Start of image data
    Serial.print(F("Image Offset: ")); Serial.println(bmpImageoffset, DEC);
    // Read DIB header
    Serial.print(F("Header size: ")); Serial.println(read32(bmpFile));
    bmpWidth  = read32(bmpFile);
    bmpHeight = read32(bmpFile);
    if(read16(bmpFile) == 1) { // # planes -- must be '1'
      bmpDepth = read16(bmpFile); // bits per pixel
      Serial.print(F("Bit Depth: ")); Serial.println(bmpDepth);
      if((bmpDepth == 24) && (read32(bmpFile) == 0)) { // 0 = uncompressed

        goodBmp = true; // Supported BMP format -- proceed!
        Serial.print(F("Image size: "));
        Serial.print(bmpWidth);
        Serial.print('x');
        Serial.println(bmpHeight);

        // BMP rows are padded (if needed) to 4-byte boundary
        rowSize = (bmpWidth * 3 + 3) & ~3;

        // If bmpHeight is negative, image is in top-down order.
        // This is not canon but has been observed in the wild.
        if(bmpHeight < 0) {
          bmpHeight = -bmpHeight;
          flip      = false;
        }

        // Crop area to be loaded
        w = bmpWidth;
        h = bmpHeight;
        if((x+w-1) >= tft.width())  w = tft.width()  - x;
        if((y+h-1) >= tft.height()) h = tft.height() - y;

        // Set TFT address window to clipped image bounds
        tft.startWrite();
        tft.setAddrWindow(x, y, w, h);

        for (row=0; row<h; row++) { // For each scanline...

          // Seek to start of scan line.  It might seem labor-
          // intensive to be doing this on every line, but this
          // method covers a lot of gritty details like cropping
          // and scanline padding.  Also, the seek only takes
          // place if the file position actually needs to change
          // (avoids a lot of cluster math in SD library).
          if(flip) // Bitmap is stored bottom-to-top order (normal BMP)
            pos = bmpImageoffset + (bmpHeight - 1 - row) * rowSize;
          else     // Bitmap is stored top-to-bottom
            pos = bmpImageoffset + row * rowSize;
          if(bmpFile.position() != pos) { // Need seek?
            tft.endWrite();
            bmpFile.seek(pos);
            buffidx = sizeof(sdbuffer); // Force buffer reload
          }

          for (col=0; col<w; col++) { // For each pixel...
            // Time to read more pixel data?
            if (buffidx >= sizeof(sdbuffer)) { // Indeed
              bmpFile.read(sdbuffer, sizeof(sdbuffer));
              buffidx = 0; // Set index to beginning
              tft.startWrite();
            }

            // Convert pixel from BMP to TFT format, push to display
            b = sdbuffer[buffidx++];
            g = sdbuffer[buffidx++];
            r = sdbuffer[buffidx++];
            //tft.pushColor(tft.color565(r,g,b)); original
            tft.pushColor(tft.color565(b,g,r)); // corrected
          } // end pixel
        } // end scanline
        tft.endWrite();
        Serial.print(F("Loaded in "));
        Serial.print(millis() - startTime);
        Serial.println(" ms");
      } // end goodBmp
    }
  }

  bmpFile.close();
  if(!goodBmp) Serial.println(F("BMP format not recognized."));
}


// These read 16- and 32-bit types from the SD card file.
// BMP data is stored little-endian, Arduino is little-endian too.
// May need to reverse subscript order if porting elsewhere.

uint16_t read16(File f) {
  uint16_t result;
  ((uint8_t *)&result)[0] = f.read(); // LSB
  ((uint8_t *)&result)[1] = f.read(); // MSB
  return result;
}

uint32_t read32(File f) {
  uint32_t result;
  ((uint8_t *)&result)[0] = f.read(); // LSB
  ((uint8_t *)&result)[1] = f.read();
  ((uint8_t *)&result)[2] = f.read();
  ((uint8_t *)&result)[3] = f.read(); // MSB
  return result;
}


void printDirectory(File dir, int numTabs) {
  while (true) {

    File entry =  dir.openNextFile();
    if (! entry) {
      // no more files
      break;
    }
    for (uint8_t i = 0; i < numTabs; i++) {
      Serial.print('\t');
    }
    Serial.print(entry.name());
    if (entry.isDirectory()) {
      Serial.println("/");
      printDirectory(entry, numTabs + 1);
    } else {
      // files have sizes, directories do not
      Serial.print("\t\t");
      Serial.println(entry.size(), DEC);
    }
    entry.close();
  }
}

Was hat es mit dem Pin10 auf sich

Sachte ich schon!
Das Datenblatt deines Prozessors oder/und die Arduino SPI Doku lese ich dir jetzt nicht vor.
Die richtigen Stichworte habe ich genannt!
Tipp: Selber lesen, dann findest du die Erklärung.

Kurzfassung:
Wenn der Pin SS ein Input ist, und der Pegel Low wird, wechselt die SPI Hardware in den Slave Modus.
Unabwendbar.
Und genau das willst du nicht.

und warum benötigt der Nano diesen nicht?

Das ist erstens kaum zu glauben, und zweitens mir völlig egal.

Hallo,

@combie: ich habe gleichartige 2 Aufbauten mit dem Nano gemacht, einen gelöteten heute an einen Freund weiter gegeben, alles funzt.

Im Adafruit Sketch (und genau diesen verwende ich) steht nix von Pin10 und ich bin auch leider eher von der einfachen Anwenderseite, kein gelernter Mikroprogrammierer.

Habe jetzt CS des Cardreaders auf Pin 10 gelegt, Cardreader wird nicht erkannt.

Zu der anderen Empfehlung mit dem Card Reader Konstruktionsfehler:

  • der Cardreader legt die SPI Kommunikation offensichtlich nicht tot. Ich habe in meinem Sketch zusätzlich zur Bitmap-Ausgabe auch noch eine reine Textausgabe eingebaut, diese wird am Display angezeigt, auch wenn der Card Reader steckt.

  • ich habe einen Cardreader umgelötet nach der heute geposteten Anleitung (Pin13 des Pegelwandlers abgelötet und auf Pin9 verbunden) - keine Besserung.

.. ich habe noch 8 Cardreader in der Bastelkiste :wink:

Hallo,

Weitere Probleme
Leider ist das nicht der einzige Konstuktionsfehler dieses Boards.

  1. Es werden zwar die 5V vom Mikrocontroller zu 3,3V für die SD-Karte übersetzt, aber nicht andersrum! In der Regel kann der Arduino einen HIGH-Zustand trotzdem problemlos erkennen, aber darauf darf man sich nicht verlassen.

Das ist jetzt noch meine aktuelle Überlegung zum Status meiner Fehlersuche.

  • der SPI Bus ist offensichtlich nicht totgelegt
  • offensichtlich stimmen beim Pro Mini die Pegel nicht, der Nano kann es aber.
    (interessant, sind doch die gleichen Controller verbaut, möge mir jemand den Unterschied erläutern...)

Kann man die Pins einfach hochziehen? Einen Level Shifter retour möchte ich mir nicht gleich antun.

Liebe Grüße
Peter

Hallo,

ich habe gerade einen schwerwiegenden Lapsus entdeckt :-[

Ich habe den Pro Mini bis jetzt nur mit meinem FTDI Kabel versorgt und dieses liefert exakt 3,3 Volt...

Damit kann der Cardreader nicht funktionieren :sunglasses:

Das Ensemble hängt jetzt am Labornetzteil, aber noch ohne Erfolg.

Der Nachteil ist nun, dass ich den Serial Monitor nicht mehr zur Verfügung habe.

Kann ich beides anschließen ohne dass etwas abraucht??

peter_basti:
Kann ich beides anschließen ohne dass etwas abraucht??

Wenn du die +5V Leitung vom USB unterbrichst gehst du kein Risiko ein,
ein Schalter in der Leitung ist ganz praktisch.

Du kannst Dir einen FTDI Kabel mit 5V besorgen.
Der FT232 kann seine Ausgänge mit 5V oder 3,3V betreiben.
Grüße Uwe

Hallo,

3,3V des FTDI-Adapters eben nicht mit dem ProMini verbinden. Die Datenverbindung braucht nur GND, TX,RX und DTR. Die Betriebsspannung für den ProMini dann eben aus einem Extra-Netzteil holen.

Ich habe meinen FTDI-Adapter so umgelötet, daß an der Stiftleiste dort immer 5V vom USB anliegen, der Jumper schaltet dann nur den Logikpegel des FTDI zwischen 3,3V und 5V. Die 3,3V vom FTDI stammen von dessen internem Regler, der liefert nur maximal 50mA.
Wenn ich 3,3V für ein angeschlossenes Modul, meist ESP, brauche, wird eben ein China-AMS1117-Schnipsel dazwischengesteckt.

Gruß aus Berlin
Michael

Guten Abend,

ich hatte dieses mein Projekt wegen Weihnachten, Familie, Grippe, Sylvester,... zurückgestellt.

Heute habe ich einen doppelten Versuchsaufbau gemacht.

1x mit Nano
1x mit Pro Mini

Zwischenstecker gebaut um auch bei ext. 5V des Pro Mini mit FTDI Kabel lesen zu können.

  • in beiden Fällen läuft der (idente) Sketch

  • in beiden Fällen läuft das Display einwandfrei

  • am Pro Mini wird nach wie vor der Cardreader nicht erkannt. Kann man auch im Monitor mitlesen.

  • der Pro Mini wird über GND und RAW nun mit 5,00 V aus dem Labornetzteil versorgt.

  • den erwähnten SS Pin10 habe ich auf HIGH gesetzt (dem Nano ist das völlig wurscht, der geht immer)

Habe jetzt keinen Plan mehr außer dass ich die Pro Mini aus dem Fenster schmeiße :grin:

Gibts noch weitere gute Ratschläge?

Liebe Grüße aus Wien
Peter