Subversion Repositories HomeAutomation

Rev

Details | Last modification | View Log | SVN | RSS feed

Rev Author Line No. Line
205 arune 1
/**
2
 *
280 arune 3
 *
4
 *
205 arune 5
 * @date    2006-11-21
280 arune 6
 * @author  Jimmy Myhrman, Anders Runeson
205 arune 7
 *  
8
 */
9
 
10
/*-----------------------------------------------------------------------------
11
 * Includes
12
 *---------------------------------------------------------------------------*/
13
/* system files */
14
#include <avr/io.h>
15
#include <avr/interrupt.h>
16
#include <avr/wdt.h>
17
#include <stdio.h>
18
/* lib files */
19
#include <can.h>
280 arune 20
//#include <serial.h>
205 arune 21
#include <timebase.h>
22
#include <ip_arp_udp_tcp.h>
23
#include <enc28j60.h>
24
#include <timeout.h>
25
#include <avr_compat.h>
26
#include <net.h>
27
 
28
// please modify the following two lines. mac and ip have to be unique
29
// in your local area network. You can not have the same numbers in
30
// two devices:
31
static uint8_t mymac[6] = {0x54,0x55,0x58,0x10,0x00,0x24};
32
static uint8_t myip[4] = {193,11,254,22};
280 arune 33
static uint16_t rmDumperPrt =1200; // remote port for dumping data
34
static uint16_t rmCan2SerPrt =1100; // remote port for Can2Serial-data
35
static uint16_t locDumperPrt =1200; // listen port 
36
static uint16_t locCan2SerPrt =1100; // listen port for Can2Serial-data
379 arune 37
static uint8_t gotdumpserver = 0;
38
static uint8_t gotcan2serserver = 0;
205 arune 39
 
40
// how did I get the mac addr? Translate the first 3 numbers into ascii is: TUX
41
 
42
static uint8_t remotemac[6];
43
static uint8_t remoteip[4];
44
 
379 arune 45
static uint8_t prgremotemac[6];
46
static uint8_t prgremoteip[4];
47
 
205 arune 48
#define BUFFER_SIZE 250
49
static uint8_t buf[BUFFER_SIZE+1];
50
 
212 arune 51
#define SEND_BUFFER_SIZE 20
52
static char sendbuf[SEND_BUFFER_SIZE+1];
53
static uint8_t buffpoint;
54
 
281 arune 55
#define C2S_START_BYTE 253
56
#define C2S_END_BYTE 250
57
 
212 arune 58
/*----------------------------------------------------------------------------
59
 * Putchar for udp
60
 * Implements a small buffer, sends packet over udp if buffer is full or
61
 * \n-char is sent.
62
 * Needs a timeout to force send.
63
 *--------------------------------------------------------------------------*/
205 arune 64
int udp_putchar(char c, FILE* stream) {
379 arune 65
    if (gotdumpserver != 0) {
212 arune 66
        sendbuf[buffpoint] = c;
67
        buffpoint++;
68
 
69
        if (c == '\n' || buffpoint > SEND_BUFFER_SIZE) {
280 arune 70
            send_udp(buf, sendbuf, buffpoint, rmDumperPrt, remotemac, remoteip);
212 arune 71
            buffpoint = 0;
205 arune 72
        }
73
    }
74
    return 0;
75
}
76
 
77
static FILE mystdout = FDEV_SETUP_STREAM(udp_putchar, NULL, _FDEV_SETUP_WRITE);
78
 
79
/*-----------------------------------------------------------------------------
80
 * Main Program
81
 *---------------------------------------------------------------------------*/
82
int main(void) {
83
 
84
    //ethernet vars
85
    uint16_t plen = 0;
86
    uint8_t ledi=0;
87
    uint8_t payloadlen=0;
212 arune 88
    buffpoint = 0;
205 arune 89
 
90
    //can vars
91
    Can_Message_t txMsg;
92
    Can_Message_t rxMsg;
93
    txMsg.Id = 3;
94
    txMsg.DataLength = 0;
95
    txMsg.RemoteFlag = 0;
96
    txMsg.ExtendedFlag = 1; //DataLength and the databytes are just what happens to be in the memory. They are never set.
212 arune 97
 
98
 
99
    uint32_t timeStamp = 0;
205 arune 100
 
212 arune 101
    Mcu_Init();
205 arune 102
    Timebase_Init();
280 arune 103
    //Serial_Init();
212 arune 104
 
105
    //alla printf ska skriva till udp
106
    stdout = &mystdout;    //set the output stream 
205 arune 107
 
108
    sei();
109
 
110
//  printf("CanInit...");
111
    if (Can_Init() != CAN_OK) {
112
//      printf("FAILED!\n");
113
    }
114
    else {
115
//      printf("OK!\n");
116
    }
117
 
118
    /* enable PB0, reset as output */
119
    DDRB|= (1<<DDB0);
120
    /* set output to gnd, reset the ethernet chip */
121
    PORTB &= ~(1<<PB0);
122
    delay_ms(20);
123
    /* set output to Vcc, reset inactive */
124
    PORTB|= (1<<PB0);
125
    delay_ms(100);
126
 
127
    // LED
128
    /* enable PB1, LED as output */
129
    DDRD|= (1<<DDD6);
130
    /* set output to Vcc, LED off */
131
    PORTD|= (1<<PD6);
132
 
212 arune 133
    //printf("Init enc\n");
205 arune 134
    /*initialize enc28j60*/
135
    enc28j60Init(mymac);
136
    delay_ms(20);
137
 
138
    /* Magjack leds configuration, see enc28j60 datasheet, page 11 */
139
    // LEDB=yellow LEDA=green
140
    //
141
    // 0x476 is PHLCON LEDA=links status, LEDB=receive/transmit
142
    enc28j60PhyWrite(PHLCON,0x476);
143
    delay_ms(20);
144
 
145
    /* set output to GND, red LED on */
146
    PORTD &= ~(1<<PD6);
147
    ledi=1;
148
 
149
    //init the ethernet/ip layer:
150
    init_ip_arp_udp_tcp(mymac,myip,80);
151
 
152
    /* main loop */
153
    while (1) {
154
        /* service the CAN routines */
155
        Can_Service();
156
 
157
        /* send CAN message and check for CAN errors once every second */
158
        if (Timebase_PassedTimeMillis(timeStamp) >= 2000) {
159
            timeStamp = Timebase_CurrentTime();
160
            /* send txMsg */
161
            //txMsg.Id++;
212 arune 162
            //txMsg.Id = 3;
163
            //Can_Send(&txMsg);
205 arune 164
 
165
        }
166
 
167
        /* check if any messages have been received */
168
        while (Can_Receive(&rxMsg) == CAN_OK) {
281 arune 169
            uint8_t i;
379 arune 170
 
171
            if (gotdumpserver != 0) {
172
                printf("MSG Received: ID=%lx, DLC=%u, EXT=%u, RTR=%u, ", rxMsg.Id, (uint16_t)(rxMsg.DataLength), (uint16_t)(rxMsg.ExtendedFlag), (uint16_t)(rxMsg.RemoteFlag));
173
                printf("data={ ");
174
                for (i=0; i<rxMsg.DataLength; i++) {
175
                    printf("%x ", rxMsg.Data.bytes[i]);
176
                }
177
                printf("}\n");
178
            }
212 arune 179
 
379 arune 180
            if (gotcan2serserver != 0) {
181
                //skicka ocks� som udppaket till rmCan2SerPrt
182
                char sendbuf2[17];
183
 
184
                sendbuf2[0] = C2S_START_BYTE;
185
                sendbuf2[1] = (uint8_t)rxMsg.Id;
186
                sendbuf2[2] = (uint8_t)(rxMsg.Id>>8);
187
                sendbuf2[3] = (uint8_t)(rxMsg.Id>>16);
188
                sendbuf2[4] = (uint8_t)(rxMsg.Id>>24);
189
                sendbuf2[5] = rxMsg.ExtendedFlag;
190
                sendbuf2[6] = rxMsg.RemoteFlag;
191
                sendbuf2[7] = rxMsg.DataLength;
192
                for (i=0; i<8; i++) {
193
                    sendbuf2[8+i] = rxMsg.Data.bytes[i];
194
                }
195
                sendbuf2[16] = C2S_END_BYTE;
196
 
197
                send_udp(buf, sendbuf2, 18, rmCan2SerPrt, prgremotemac, prgremoteip);
198
            }
205 arune 199
        }
200
 
212 arune 201
        //test-debug-kod
202
        if ((enc28j60Read(EIR) & EIR_TXERIF)) {
203
            //printf("EIR_TXERIF set!\n");
204
            if ((enc28j60Read(ECON1) & ECON1_TXRTS)) {
205
                //printf("ECON1_TXRTS set!\n");
206
            }
207
        }
208
        if ((enc28j60Read(EIR) & EIR_TXIF)) {
209
            //printf("EIR_TXIF set! ");
210
        }
211
        if ((enc28j60Read(ESTAT) & ESTAT_TXABRT)) {
212
            //printf("ESTAT_TXABRT set!\n");
213
            //printf("MACLCON1: %i\n", enc28j60Read(MACLCON1));
214
            enc28j60WriteOp(ENC28J60_BIT_FIELD_CLR, ESTAT, ESTAT_TXABRT);
215
        }
216
 
205 arune 217
        // get the next new packet:
218
        plen = enc28j60PacketReceive(BUFFER_SIZE, buf);
219
 
220
        /*plen will ne unequal to zero if there is a valid
221
         * packet (without crc error) */
222
        if(plen!=0){
223
            // arp is broadcast if unknown but a host may also
224
            // verify the mac address by sending it to 
225
            // a unicast address.
226
            if(eth_type_is_arp_and_my_ip(buf,plen)){
227
                    make_arp_answer_from_request(buf);
228
            } else {
229
                // check if ip packets (icmp or udp) are for us:
230
                if(eth_type_is_ip_and_my_ip(buf,plen)!=0){
231
 
232
                    if(buf[IP_PROTO_P]==IP_PROTO_ICMP_V && buf[ICMP_TYPE_P]==ICMP_TYPE_ECHOREQUEST_V){
233
                            // a ping packet, let's send pong
234
                            make_echo_reply_from_request(buf,plen);
212 arune 235
                            //txMsg.Id = 6;
236
                            //Can_Send(&txMsg);
205 arune 237
 
238
                    }
239
                    if (buf[IP_PROTO_P]==IP_PROTO_UDP_V){
240
                        payloadlen=buf[UDP_LEN_L_P]-UDP_HEADER_LEN;
379 arune 241
                        uint8_t i = 0;
242
 
243
                        //om port 1100 (programmeringsporten)
280 arune 244
                        if ((buf[UDP_DST_PORT_H_P]==((locCan2SerPrt>>8) & 0xff)) && (buf[UDP_DST_PORT_L_P] == (locCan2SerPrt & 0xff))) {
379 arune 245
                            while(i<6){
246
                                prgremotemac[i]=buf[ETH_SRC_MAC +i];
247
                                i++;
248
                            }
249
                            i=0;
250
                            while(i<4){
251
                                prgremoteip[i]=buf[IP_SRC_P +i];
252
                                i++;
253
                            }
254
                            gotcan2serserver = 1;
255
 
256
                            if ((buf[UDP_DATA_P]==C2S_START_BYTE) && (buf[UDP_DATA_P+16]==C2S_END_BYTE) && (payloadlen==17)) {
257
                                Can_Message_t cm;
258
                                //cm.Id = 0;
259
                                cm.DataLength = buf[UDP_DATA_P+7];
260
                                cm.RemoteFlag = buf[UDP_DATA_P+6];
261
                                cm.ExtendedFlag = buf[UDP_DATA_P+5];
262
                                cm.Id = (uint32_t)buf[UDP_DATA_P+1] + ((uint32_t)buf[UDP_DATA_P+2] << 8) + ((uint32_t)buf[UDP_DATA_P+3] << 16) + ((uint32_t)buf[UDP_DATA_P+4] << 24);
263
                                uint8_t i;
264
                                for (i = 0; i < cm.DataLength; i++) {
265
                                    cm.Data.bytes[i] = buf[UDP_DATA_P+8+i];
266
                                }
267
                                Can_Send(&cm);
268
 
269
                                if (gotdumpserver != 0) {
270
                                    printf("MSG Received: ID=%lx, DLC=%u, EXT=%u, RTR=%u, ", cm.Id, (uint16_t)(cm.DataLength), (uint16_t)(cm.ExtendedFlag), (uint16_t)(cm.RemoteFlag));
271
                                    printf("data={ ");
272
                                    for (i=0; i<cm.DataLength; i++) {
273
                                        printf("%x ", cm.Data.bytes[i]);
281 arune 274
                                    }
379 arune 275
                                    printf("}\n");
281 arune 276
                                }
277
                            }
379 arune 278
                        //om port 1200 (dumparporten) 
279
                        } else if ((buf[UDP_DST_PORT_H_P]==((locDumperPrt>>8) & 0xff)) && (buf[UDP_DST_PORT_L_P] == (locDumperPrt & 0xff))) {
280
                            if (gotdumpserver == 0) {
212 arune 281
                                while(i<6){
282
                                    remotemac[i]=buf[ETH_SRC_MAC +i];
283
                                    i++;
284
                                }
285
                                i=0;
286
                                while(i<4){
287
                                    remoteip[i]=buf[IP_SRC_P +i];
288
                                    i++;
289
                                }
290
                                i=0;
291
 
379 arune 292
                                gotdumpserver = 1;
280 arune 293
                                make_udp_reply_from_request(buf,"Got server",10,rmDumperPrt);
212 arune 294
                            } else {
280 arune 295
                                make_udp_reply_from_request(buf,"Already got server",18,rmDumperPrt);
212 arune 296
                            }
205 arune 297
                        }
298
                    }                      
299
                }
300
            }
301
        }
302
 
303
 
304
 
305
 
306
    }
307
 
308
    return 0;
309
}