Mikrocontroller und Digitale Elektronik
›
Thread
MCP23S17 ansteuern
AE
Alex E.
(alex_e)
OP
07.02.2012 20:19
#2538807
Hallo,
hab nun schon alles durchgeschaut und bekomme es nicht hin.
MCP23S17 ist an SPI angeschlossem und SS an PB0(µC), Reset auf Vcc.
Adress-Pins am MCP sind offen, liegen im Low-Pegel(gemessen).
Sollte aber beim ersten ansteuern erstmal egal sein, da IOCON.HAEN auf 0
nach POR liegt.
hab dem atmega324PA mit 3.3V im einsatz...
Verwende folgenden Code(aus einem anderen Thread): 1 #include <avr/io.h>
2 #include <stdio.h>
3 #include <avr/interrupt.h>
4 #include <avr/eeprom.h>
5 #include <avr/delay.h>
6 #include <string.h>
7 #include "MCP23S17.h"
8
9 void conf_mcp_send ( uint8_t addr , uint8_t art , uint8_t pa , uint8_t pb )
10 {
11 cli ();
12 //uint8_t send_addr;
13 //send_addr=addr && 0b111;
14 //addr= send_addr<<1;
15 MCP_CS_ON ();
16 _delay_us ( 50 );
17 SPI_WRITE ((( addr ) << 1 ) | 0x40 );
18 SPI_WAIT ();
19 SPI_WRITE ( art );
20 SPI_WAIT ();
21 SPI_WRITE ( pa );
22 SPI_WAIT ();
23 SPI_WRITE ( pb );
24 SPI_WAIT ();
25 MCP_CS_OFF ();
26 _delay_us ( 2 );
27 }
28
29 void mcp_send ( uint8_t addr , uint8_t pa , uint8_t pb )
30 {
31 cli ();
32 //uint8_t send_addr;
33 //send_addr=addr && 0b111;
34 //addr= send_addr<<1;
35 MCP_CS_ON ();
36 //_delay_us(20);
37 SPI_WRITE (( addr << 1 ) | 0x40 );
38 SPI_WAIT ();
39 SPI_WRITE ( 0x12 );
40 SPI_WAIT ();
41 SPI_WRITE ( pa );
42 SPI_WAIT ();
43 SPI_WRITE ( pb );
44 SPI_WAIT ();
45 //_delay_us(20);
46 MCP_CS_OFF ();
47 _delay_us ( 2 );
48
49 }
50
51 int mcp_rec ( uint8_t addr )
52 {
53 cli ();
54 uint8_t timeout ;
55 uint8_t by ;
56 uint8_t bx ;
57 MCP_CS_ON ();
58 //_delay_us(20);
59 SPI_WRITE (( addr << 1 ) | 0x41 );
60 SPI_WAIT ();
61 SPI_WRITE ( 0x12 );
62 SPI_WAIT ();
63
64 timeout = 255 ;
65
66 //wait for response
67 do
68 {
69 SPI_WRITE ( DUMMY_WRITE );
70 SPI_WAIT ();
71 by = SPI_DATA_REGISTER ;
72 timeout -- ;
73 if ( timeout == 0 ) break ; // no response
74 } while ( by == DUMMY_WRITE );
75
76 do
77 {
78 SPI_WRITE ( DUMMY_WRITE );
79 SPI_WAIT ();
80 bx = SPI_DATA_REGISTER ;
81 timeout -- ;
82 if ( timeout == 0 ) break ; // no response
83 } while ( bx == DUMMY_WRITE );
84 MCP_CS_OFF ();
85 _delay_us ( 2 );
86
87 return by | bx << 8 ;
88
89 }
90
91 void mcp_int_on ()
92 {
93 cli ();
94 conf_mcp_send ( 3 , MCP_GPINTEN , 0XFF , 0XFF );
95 conf_mcp_send ( 3 , MCP_DEFVAL , 0X00 , 0X00 );
96 }
97
98 void initmcp ( uint8_t addr )
99 {
100 cli ();
101 // SPCR SPI Controlregister
102 // SPIE=0; //No SPI Interrupt
103 // SPE=1; //SPI Enable
104 // DORD=0; //Send MSB first
105 // MSTR=1; //I am the master !
106 // CPOL=0; //SCK low if IDLE
107 // CPHA=0; //SPI Mode 0
108 // SPR1=1; //SPI Clock = f/128 = 125kHz @16MHz Clock
109 // SPR0=1; //or f/64 if SPI2X = 1 in SPSR register
110
111
112 SPI_CTRL_REGISTER = ( 1 << SPE0 ) | ( 1 << MSTR0 ) | ( 1 << SPR00 ) | ( 1 << SPR10 );
113
114 // SPSR SPI Statusregister
115 // SPI2X=0; // No double speed
116 _delay_ms ( 1 );
117 /*Teste*******/
118 //conf_mcp_send(addr,MCP_IOCON,0b00000000,0b00000000);
119 conf_mcp_send ( addr , MCP_IODIR , 0xf8 , 0xff );
120 conf_mcp_send ( addr , MCP_GPPU , 0XFF , 0XFF );
121 mcp_send ( addr , 0x07 , 0x00 );
122 /******************************/
123
124 //conf_mcp_send(1,MCP_IODIR,0X00,0X00);
125 //
126 //conf_mcp_send(2,MCP_IOCON,0x40,0x40);
127 //conf_mcp_send(2,MCP_IODIR,0X00,0X00);
128 //
129 //conf_mcp_send(0,MCP_IOCON,0b01000000,0b01000000);
130 //conf_mcp_send(3,MCP_IODIR,0XFF,0XFF);
131 //conf_mcp_send(3,MCP_IPOL,0XFF,0XFF);
132 //conf_mcp_send(0,MCP_GPPU,0XFF,0X00);
133
134 /*EIMSK = (1<<INT2);
135 EIFR = (1<<INTF2);
136 EICRA |=(0<<ISC20);
137 EICRA |=(0<<ISC21);
138
139
140
141 /* Move interrupts to Boot Flash section */
142 }
1 #ifndef MCP23S17_H_
2 #define MCP23S17_H_
3
4 //Deklaration MCP Register
5 /*
6 ' MCP23S17 Register RO=ReadOnly
7 ' Adresse 00 01 IODIR Richtung Port a/b 0=Output 1=Input
8 ' Adresse 02 03 IPOL Polarität 1=umgekehrt
9 ' Adresse 04 05 GPINTEN Interrupt aktivieren 1=an 0=aus
10 ' Adresse 06 07 DEFVAL Vergleichsregister für Interrupt
11 ' Adresse 08 09 INTCON 1=PIN<->DEFVAL 0=PIN neu <->PIN alt
12 ' Adresse 0A 0B IOCON Configuration
13 ' Adresse 0C 0D GPPU PullUp 1=aktiv 0= aus
14 ' Adresse 0E 0F INRF Interrupt Flag register RO
15 ' Adresse 10 11 INTCAP Interrupt Capture Register RO
16 ' Adresse 12 13 GPIO Port Werte RW
17 ' Adresse 14 14 OLAT Output Latch Register
18 */
19 #define MCP_IODIR 0x00
20 #define MCP_IPOL 0x02
21 #define MCP_GPINTEN 0x04
22 #define MCP_DEFVAL 0x06
23 #define MCP_INTCON 0x08
24 #define MCP_IOCON 0x0A
25 #define MCP_GPPU 0x0C
26 #define MCP_INRF 0x0E
27 #define MCP_INTCAP 0x10
28 #define MCP_GPIO 0x12
29 #define MCP_OLAT 0x14
30
31 #define DUMMY_WRITE (uint8_t)(0xFF)
32 // Port definition
33 #define MCP_CS_BIT 0
34 #define MCP_CS_PORT PORTB
35 #define MCP_CS_DDR DDRB
36
37 //#define MCP_RESET_BIT 0
38 //#define MCP_RESET_PORT PORTB
39 //#define MCP_RESET_DDR DDRB
40
41 #define MCP_INTERRUPT_BIT 2
42 #define MCP_INTERRUPT_PORT PORTB
43 #define MCP_INTERRUPT_DDR DDRB
44
45 #ifndef cbi
46 #define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
47 #endif
48 #ifndef sbi
49 #define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))
50 #endif
51
52 #define MCP_CS_INIT() { cbi(MCP_INTERRUPT_DDR,MCP_INTERRUPT_BIT); \
53 sbi(MCP_CS_PORT,MCP_CS_BIT); \
54 sbi(MCP_CS_DDR,MCP_CS_BIT); /*/
55 sbi(MCP_RESET_PORT,MCP_RESET_BIT); /
56 sbi(MCP_RESET_DDR,MCP_RESET_BIT);*/ }
57
58 #define MCP_CS_ON() cbi(MCP_CS_PORT,MCP_CS_BIT);
59 #define MCP_CS_OFF() sbi(MCP_CS_PORT,MCP_CS_BIT);
60
61 //#define MCP_RESET_ON() cbi(MCP_RESET_PORT,MCP_RESET_BIT);
62 //#define MCP_RESET_OFF() sbi(MCP_RESET_PORT,MCP_RESET_BIT);
63
64 #define SPI_CTRL_REGISTER SPCR0
65 #define SPI_STATUS_REGISTER SPSR0
66 #define SPI_DATA_REGISTER SPDR0
67 #define SPI_STATUS_IF_BIT SPIF0
68
69 #define SPI_WRITE(a) { SPI_DATA_REGISTER=(a); }
70 #define SPI_WAIT() { while(! ( SPI_STATUS_REGISTER & (1<<SPI_STATUS_IF_BIT) ) ); }
71
72 void conf_mcp_send ( uint8_t addr , uint8_t art , uint8_t pa , uint8_t pb );
73 void mcp_send ( uint8_t addr , uint8_t pa , uint8_t pb );
74 int mcp_rec ( uint8_t addr );
75 void mcp_int_on ();
76 void initmcp ( uint8_t addr );
77
78 #endif /* MCP23S17_H_ */
Vielen Dank für hilfreiche Tipps;-)
H
holger
Gast
07.02.2012 20:56
#2538879
1 //wait for response
2 do
3 {
4 SPI_WRITE ( DUMMY_WRITE );
5 SPI_WAIT ();
6 by = SPI_DATA_REGISTER ;
7 timeout -- ;
8 if ( timeout == 0 ) break ; // no response
9 } while ( by == DUMMY_WRITE );
Kommt mir bekannt vor;)
Nur mal zum Verständnis: Der MCP23S17 ist keine
SD Karte!
AE
Alex E.
(alex_e)
OP
07.02.2012 21:04
#2538896
ja, es wurde ein teil einer sdcard-implementierung genutzt.
ich benutz aber momentan nur die Funktion initmcp(0);
Sollte dann ja gerade meine Adresspins ansteuerung, geht aber nicht;-(
AE
Alex E.
(alex_e)
OP
07.02.2012 21:16
#2538926
Sorry Jungs...
eine Zeile hat das Problem gelöst;-)
DDRB |= (1<<PINB0);
Antwort schreiben
Bitte melde dich an, um einen Beitrag zu schreiben.
Noch kein Account?
Die Registrierung ist kostenlos und dauert nur eine Minute.
Jetzt registrieren