Forum: Mikrocontroller und Digitale Elektronik 18Bit per HW SPI?


von Gee (Gast)


Lesenswert?

Habe ein OLED Display (4x20 Zeichen) und Probleme bei der Ansteuerung 
per SPI..

Mein Kontroller unterstützt 8 und 16Bit SPI in HW.

Im Datenblatt sieht es so aus als müsse man 18Bits senden weil die RW 
und RS Bits mit über den Bus laufen sollen was in sofern aber keinen 
Sinn macht denn bei anderen Displays ist das nicht so.

Das Datenblatt ist hier: 
http://www.lcd-module.de/fileadmin/pdf/doma/oled.pdf

von Falk B. (falk)


Lesenswert?

@Gee (Gast)

>Im Datenblatt sieht es so aus als müsse man 18Bits senden weil die RW
>und RS Bits mit über den Bus laufen sollen

Sieht so aus.

> was in sofern aber keinen
>Sinn macht denn bei anderen Displays ist das nicht so.

Bei dem aber schon. Da haben die Entwickler des ICs mal wieder ne 
"schöne" Sonderlösung erfunden. Man hätte auch einfach Nx8 Bit nehmen 
können und ein paar Bits ungenutzt lassen. Naja.

Da mußt du wohl das SPI in Software machen. So what! Das Display ist 
sowieso nur alphanumerisch und im Vergleich zur CPU schnachlangsam (max. 
3,3 MHz SPI-Takt)

von Rainer U. (r-u)


Lesenswert?

Gee schrieb:
> Im Datenblatt sieht es so aus als müsse man 18Bits senden weil die RW
> und RS Bits mit über den Bus laufen sollen

Na dann sendest Du halt 18 bit - wenn es exakt 18 sein müssen, per 
Software-SPI. Evtl. stört es nicht, wenn Du 24 statt 18 bots sendest - 
dann eben 3 Bytes in Hardware.

von Einer K. (Gast)


Lesenswert?

Rainer U. schrieb:
> Evtl. stört es nicht, wenn Du 24 statt 18 bots sendest -
> dann eben 3 Bytes in Hardware.

Richtig!

Zusehen, dass die gewünschten Bits zum Schluss kommen, dann werden die 
ersten (dummybits) raus, oder ins Nirvana, geschoben. Das macht den Bits 
nichts aus.

von Arduinoquäler (Gast)


Lesenswert?

Arduino F. schrieb:
> Das macht den Bits nichts aus.

Die armen Bits ..... werden einfach ins Nirwana geschickt ....

von Gee (Gast)


Lesenswert?

Na prima ^^ Also ich würde mal die 24Bit Lösung probieren.. was ist 
sinnvoller die Dummybits 1 oder 0 zu setzen?

von Arduinoquäler (Gast)


Lesenswert?

Gee schrieb:
> was ist sinnvoller die Dummybits 1 oder 0 zu setzen?

Darüber streiten sich die Geleerten.

Mühevolle langwierige Testreihen bringen Erleuchtung.

von Gee (Gast)


Lesenswert?

hier ist übrigens der Beispiel Code zum Display.. bin aber nur im 
Assembler mächtig
1
//-----------------------------------------------------
2
//File: lcd_spi.c
3
//Auth: ELECTRONIC ASSEMBLY JM
4
//DATE: 04-17-2014
5
//-----------------------------------------------------
6
7
//---Includes---
8
#include "sfr_r825.h"
9
#include "define.h"
10
11
#include "lcd_spi.h"
12
13
//-----------------------------------------------------
14
//Attention, you need to change solder bridges!
15
//-----------------------------------------------------
16
17
18
static void WriteIns    (char ins);
19
static void WriteData    (char data);
20
unsigned char CheckBusy    (void);
21
static void SPI_put (unsigned int dat);
22
static unsigned char SPI_get (unsigned char rs);
23
24
//--- module global varibles ---
25
26
27
28
//-----------------------------------------------------
29
//Func: initDispl()
30
//Desc: inits Display
31
//-----------------------------------------------------
32
void initDispl(void)
33
{
34
  unsigned char i;
35
36
  //Port init (dd -> datadirection register; 1 output, 0 input)
37
  ddSID = 1;
38
  SID = 1;
39
  ddSOD = 0;
40
  ddSCLK = 1;
41
  SCLK = 1;
42
  ddCS = 1;
43
  CS = 1;
44
  
45
  //init Display
46
  WriteIns(0x38+3);  //function set european chararacter set
47
  WriteIns(0x08);  //display off
48
  WriteIns(0x06);  //entry mode set increment cursor by 1 not shifting display
49
  WriteIns(0x17);  //Character mode and internel power on (have to turn on internel power to get the best brightness)
50
  WriteIns(0x01);  //clear display
51
  WriteIns(0x02);  //return home
52
  WriteIns(0x0C);  //display on
53
54
  ClrDisplay();
55
  DisplayOnOff(DISPLAY_ON | CURSOR_ON | BLINK_ON);
56
}
57
58
//-----------------------------------------------------
59
//Func: WriteChar(character)
60
//Desc: sends a single character to display
61
//-----------------------------------------------------
62
void WriteChar (char character)
63
{
64
  WriteData(character);
65
}
66
67
//-----------------------------------------------------
68
//Func: WriteString(string)
69
//Desc: sends a string to display, must be 0 terminated
70
//-----------------------------------------------------
71
void WriteString(_far char * string)
72
{
73
  do
74
  {
75
    WriteData(*string++);
76
  }
77
  while(*string);
78
}
79
80
81
//-----------------------------------------------------
82
//Func: SetPostion(postion)
83
//Desc: set postion
84
//-----------------------------------------------------
85
void SetPostion(char pos)
86
{
87
  WriteIns(LCD_HOME_L1+pos);
88
}
89
90
//-----------------------------------------------------
91
//Func: DisplayOnOff(control)
92
//Desc: use definitions of header file to set display
93
//-----------------------------------------------------
94
void DisplayOnOff(char data)
95
{
96
  WriteIns(0x08+data);
97
}
98
99
//-----------------------------------------------------
100
//Func: DefineCharacter(memory postion, character data)
101
//Desc: stores an own defined character
102
//-----------------------------------------------------
103
void DefineCharacter(unsigned char postion, unsigned char *data)
104
{
105
  unsigned char i=0;
106
  WriteIns(0x40+8*postion);
107
108
  for (i=0; i<8; i++)
109
  {
110
    WriteData(data[i]);
111
  }
112
  SetPostion(LINE1);
113
}
114
//-----------------------------------------------------
115
//Func: ClrDisplay
116
//Desc: Clears entire Display content and set home pos
117
//-----------------------------------------------------
118
void ClrDisplay(void)
119
{
120
  WriteIns(0x01);
121
  SetPostion(LINE1);
122
}
123
124
//-----------------------------------------------------
125
//Func: SetROM
126
//Desc: Changes the Rom code (CG: 0,1,2,3)
127
//---------------------------------------------------
128
void SetROM (unsigned char rom)
129
{
130
  
131
  WriteIns(0x38+ (rom & 0x03));
132
}
133
134
//-----------------------------------------------------
135
//Func: WriteIns(instruction)
136
//Desc: sends instruction to display
137
//-----------------------------------------------------
138
static void WriteIns(char ins)
139
{
140
  CheckBusy();
141
  
142
  SPI_put(0x0000 + ins);
143
}
144
145
//-----------------------------------------------------
146
//Func: WriteData(data)
147
//Desc: sends data to display
148
//-----------------------------------------------------
149
static void WriteData(char data)
150
{
151
  CheckBusy();
152
  
153
  SPI_put(0x0200 + data);
154
  
155
}
156
157
//-----------------------------------------------------
158
//Func: CheckBusy()
159
//Desc: checks if display is idle
160
//-----------------------------------------------------
161
unsigned char CheckBusy(void)
162
{
163
  unsigned char readData = 1;
164
165
  do
166
  {
167
    readData = SPI_get(0); 
168
169
  }while(readData&0x80); //check for busyflag
170
171
  return readData;
172
}
173
174
//-----------------------------------------------------
175
//Func: SPI_put()
176
//Desc: sends data over the spi interface
177
//-----------------------------------------------------
178
static void SPI_put (unsigned int dat)
179
{
180
  unsigned char i = 9;
181
  CS = 0;
182
  
183
  do
184
  {
185
    SCLK = 0;   //Clock puls > 300nsec
186
    SID = dat >> i;
187
    SCLK = 1;
188
  }while(i--);
189
  
190
  CS = 1;
191
}
192
193
//-----------------------------------------------------
194
//Func: SPI_get()
195
//Desc: receives interface
196
//-----------------------------------------------------
197
static unsigned char SPI_get (unsigned char rs)
198
{
199
  unsigned char i = 7;
200
  unsigned char ret = 0;
201
  CS = 0;
202
  
203
  SCLK = 0;
204
  SID = rs;
205
  SCLK = 1;
206
  SCLK = 0;
207
  SID = 1;   //RW-Bit
208
  SCLK = 1;
209
  
210
  //8 dummy reads
211
  do
212
  {
213
    SCLK = 0;
214
    SCLK = 1;
215
  }while(i--);
216
  
217
  i=7;
218
  //read data
219
  do
220
  {
221
    SCLK = 0;
222
    SCLK = 1;
223
    ret |= SOD << i;    
224
  }while(i--);
225
  
226
  CS = 1;
227
  
228
  return ret;
229
}

von Gee (Gast)


Lesenswert?

Im Moment schicke ich 0x00 0x00 INS und 0x02 0x00 DATA (0x00 0x02 DATA 
habe ich auch schon probiert)

von Pandur S. (jetztnicht)


Lesenswert?

Aeh. Ja. Grossartig.
Und geht's ?
Falls nicht, per Hand (SW) rauslassen

Und .. normalerweise ist noch ein timing zu beachten. Insbesondere ist 
eine sehr lange Zeit nach dem Reset einhalten

: Bearbeitet durch User
von Gee (Gast)


Lesenswert?

Soo.. wollte mich nochmal meld.

Es funktioniert jetzt per 10 Bit SW SPI. Anders als im Datenblatt 
beschrieben nutze ich die 10Bit sowohl für Instruktions als auch für 
Daten.

Die ersten beiden Bits sind RW und RS und danach folgen Bit7..0

von Gee (Gast)


Lesenswert?

Achja und noch was wichtiges.. ich schicke vor der erst init 100 Dummy 
clocks (0x00) sonst funktioniert es nicht immer zuverlässig

von spess53 (Gast)


Lesenswert?

HI

>Achja und noch was wichtiges.. ich schicke vor der erst init 100 Dummy
>clocks (0x00) sonst funktioniert es nicht immer zuverlässig

Habe ich bei Soft-SPI noch nie gebraucht.

Könnte aber sein das der Displaycontroller, im Datenblatt steht 
'INTEGRIERTER KONTROLLER (HD44780-ÄHNLICH)', wie dieser zwischen dem 
Einschalten und der Initialisierung eine gewisse Wartezeit braucht.

MfG Spess

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
Noch kein Account? Hier anmelden.