Subversion Repositories svnkaklik

Rev

Rev 372 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log

Rev Author Line No. Line
365 kakl 1
/*****************************************************************************/
2
/*
3
 *  vector.cpp - Control program for Vector robot
4
 *
5
 *      Copyright (C) 2007 KAKL
6
 *
7
 *      This program is free software; you can redistribute it and/or modify
8
 *      it under the terms of the GNU General Public License as published by
9
 *      the Free Software Foundation; either version 2 of the License, or
10
 *      (at your option) any later version.
11
 *
12
 *      This program is distributed in the hope that it will be useful,
13
 *      but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 *      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
 *      GNU General Public License for more details.
16
 *
17
 */
18
/*****************************************************************************/
19
 
20
#include <iostream>
21
#include <getopt.h>
22
#include <errno.h>
23
#include <string.h>
24
#include <pthread.h>
25
#include <stdio.h>
26
#include <stdlib.h>
27
#include <unistd.h>
28
#include "linux/i2c-dev.h"
29
#include "linux/i2c.h"
30
#include <sys/ioctl.h>
31
#include <sys/types.h>
32
#include <sys/stat.h>
33
#include <fcntl.h>
34
#include "geocalc.h"
369 kakl 35
#include "track.h"
365 kakl 36
 
37
using namespace std;
38
 
39
 
40
#define BC_Addr	    0x0B
377 kakl 41
#define US1_Addr	(0xE2>>1)
42
#define US2_Addr	(0xE4>>1)
43
#define US3_Addr	(0xE6>>1)
44
#define CMPS_Addr   (0xC0>>1)
45
#define M1	        (0xA0>>1)
46
#define M2	        (0xA2>>1)
365 kakl 47
 
377 kakl 48
#define SEVER 122
372 kakl 49
 
367 kakl 50
char vystup[50];
51
pthread_t thread_1, thread_2, thread_3;
365 kakl 52
FILE *pRouraO,*pRouraI;
53
unsigned int vzdalenost;
54
char command,ble;
377 kakl 55
int param;
365 kakl 56
int file;
377 kakl 57
double nord, east;
58
int done; // vlajka, ze se neco udelalo
59
int last_cross; // posledni krizovatka
365 kakl 60
 
367 kakl 61
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
62
 
365 kakl 63
void *print_tele(void *unused);
367 kakl 64
void *gps(void *unused);
366 kakl 65
//void *sensors(void *unused);
365 kakl 66
 
67
void I2C_addr (int Addr)
68
{
69
    if (ioctl(file, I2C_SLAVE, Addr) == -1)
70
    {
71
        fprintf(stderr, "Failed to set address to 0x%02x.\n", Addr);
72
        exit(-5);
73
    }
74
}
75
 
372 kakl 76
void go (int Addr, int speed) // nastavi rychlost motoru
367 kakl 77
{
78
    char Buf[1];
79
 
80
    I2C_addr (Addr);
81
    Buf[0]=speed;
82
    write(file, Buf, 1);
83
}
84
 
372 kakl 85
unsigned int echo(int Addr)  // precte vzdalenost z US cidla
371 kakl 86
{
87
    char Buf[3];
88
 
89
    I2C_addr(Addr);
90
    Buf[0]=0x0;
91
    Buf[1]=0x51;
92
    write(file, Buf, 2);
93
    usleep(80000);
94
    read(file, Buf, 3);
95
    return (Buf[1]*256+Buf[2]);
96
}
97
 
377 kakl 98
unsigned char read_azimut_mag()  // precte azimut z kompasu
99
{
100
    char Buf[3];      // promena pro manipulaci s i2c
101
 
102
    I2C_addr(CMPS_Addr);
103
    Buf[0]=1;
104
    write(file,Buf,1);
105
    read(file, Buf,1);
106
    return (Buf[0]-SEVER);
107
}
108
 
109
void calib()  // kalibrace kompasu
110
{
111
    char Buf[3];      // promena pro manipulaci s i2c
112
 
113
    I2C_addr(CMPS_Addr);
114
    Buf[0]=15;
115
    Buf[1]=0xFF;
116
    write(file,Buf,2);
117
}
118
 
119
void TL (unsigned char azimut2)
120
{
121
    unsigned char azimut1;
122
 
123
    go(M1, 0);
124
    go(M2, 120);
125
    do
126
    {
127
        azimut1=read_azimut_mag();
128
//printf("az1: %d - az2: %d\n", azimut1, azimut2);
129
        usleep(10000);
130
    } while( (azimut1!=azimut2)&&((azimut1+1)!=azimut2)&&((azimut1+2)!=azimut2)&&((azimut1+3)!=azimut2) );
131
    go(M1, 0);
132
    go(M2, 0);
133
}
134
 
135
void TR (unsigned char azimut2)
136
{
137
    unsigned char azimut1;
138
 
139
    go(M1, 120);
140
    go(M2, 0);
141
    do
142
    {
143
        azimut1=read_azimut_mag();
144
        usleep(10000);
145
    } while( (azimut1!=azimut2)&&((azimut1-1)!=azimut2)&&((azimut1-2)!=azimut2)&&((azimut1-3)!=azimut2) );
146
    go(M1, 0);
147
    go(M2, 0);
148
}
149
 
371 kakl 150
void FindNearestCrossing(void)
151
{
152
    int n;
377 kakl 153
    double dist, pomN, pomE;
371 kakl 154
 
377 kakl 155
    pthread_mutex_lock(&mutex);         // prepis souradnic do pracovnich promennych
156
    pomN=nord; pomE=east;
157
    pthread_mutex_unlock(&mutex);
158
    if ( GeoCalc::EllipsoidDistance(pomN, pomE, cros[last_cross].n, cros[last_cross].e)>((double)cros[n].dia+5) ) done=0; // znovu naviguj, pokud si dal nez... od krizovatky
371 kakl 159
    n=0;
160
    do
161
    {
162
        if (0==cros[n].id) break;
377 kakl 163
        dist=GeoCalc::EllipsoidDistance(pomN, pomE, cros[n].n, cros[n].e);
164
        if (dist <= (double)cros[n].dia)
371 kakl 165
        {
377 kakl 166
//printf("Point ID: %d - Distance: %f\n",cros[n].id, dist);
167
            if (done==0)
168
            {
169
                last_cross=n;
170
                #include "nav.h"
171
                done=1;
172
            }
371 kakl 173
            break;
174
        }
175
    } while(++n<POINTS);
176
}
177
 
372 kakl 178
int i2c_init()   // zinicializuje i2c
365 kakl 179
{
180
	file = open("/dev/i2c-0", O_RDWR);
181
	if (file < 0)
182
	{
183
		cerr << "Could not open /dev/i2c-0." << endl;
184
		return -1;
185
	}
372 kakl 186
	return 0;
187
}
365 kakl 188
 
372 kakl 189
void turnL(unsigned char angle, signed char speed)    // otoci robota o zadany uhel
190
{
191
int azimut;
192
 
193
    go(M1, speed);
194
    go(M2, -speed);
195
    azimut=read_azimut_mag();
196
    while(read_azimut_mag() >= (azimut + angle)) usleep(10000);
197
    go(M1, 0);
198
    go(M2, 0);
199
}
200
 
201
void turnR()    // otoci robota o zadany uhel
202
{
203
}
204
 
205
int main(int argc, char *argv[], char *envp[])
206
{
207
    int filtr;
208
    signed char test;
209
 
210
	fprintf(stdout, "\n **** Starting Vector Control Programm **** \n \r");
211
 
212
    i2c_init();
213
 
377 kakl 214
    last_cross=0;
215
    command=0;
216
    filtr=0;
217
    done=0;
218
 
365 kakl 219
    pthread_create(&thread_1, NULL, print_tele, NULL);
369 kakl 220
    pthread_create(&thread_3, NULL, gps, NULL);
365 kakl 221
//    pthread_create(&thread_2, NULL, sensors, NULL);
222
 
223
    while(true)
224
    {
367 kakl 225
        switch (command)
366 kakl 226
        {
367 kakl 227
            case 'f':   // forward
377 kakl 228
                go(M1, param);
229
                go(M2, param);
230
                sleep(1);
367 kakl 231
                command=0;
232
                break;
377 kakl 233
 
367 kakl 234
            case 'b':   // backward
377 kakl 235
                go(M1, -param);
236
                go(M2, -param);
237
                sleep(1);
367 kakl 238
                command=0;
239
                break;
377 kakl 240
 
372 kakl 241
            case 'v':   // volnobeh
242
                go(M1, -128);
243
                go(M2, -128);
244
                command=0;
245
                break;
377 kakl 246
 
372 kakl 247
            case 's':   // stop
367 kakl 248
                go(M1, 0);
249
                go(M2, 0);
250
                command=0;
251
                break;
377 kakl 252
 
253
            case 'l':   // left
254
                TL(param);
369 kakl 255
                command=0;
256
                break;
372 kakl 257
 
377 kakl 258
            case 'r':   // right
259
                TR(param);
260
                command=0;
261
                break;
262
 
263
            case 'c':   // kalibrace kompasu
264
                calib();
265
                command=0;
266
                break;
267
 
372 kakl 268
            case 't':   // test
269
                for(test=0;test<127;test++)
270
                {
271
                    go(M1, test);
272
                    go(M2, test);
273
                    usleep(10000);
274
                };
275
                go(M1, 127);
276
                go(M2, 127);
277
                for(test=127;test>-128;test--)
278
                {
279
                    go(M1, test);
280
                    go(M2, test);
281
                    usleep(10000);
282
                };
283
                go(M1, -128);
284
                go(M2, -128);
285
                command=0;
286
                break;
287
 
367 kakl 288
            case 'g':
372 kakl 289
    usleep(180000);  // simulace ostatnich  cidel (zdrzeni)
290
 
377 kakl 291
//!!!KAKL                FindNearestCrossing();
372 kakl 292
 
371 kakl 293
                vzdalenost=echo(US3_Addr);
294
                if ((vzdalenost>60)&&(vzdalenost<80))
367 kakl 295
                {
371 kakl 296
                    go(M1, 60);
297
                    go(M2, 60);
298
                    filtr=0;
367 kakl 299
                    break;
300
                };
371 kakl 301
                if ((vzdalenost>30)&&(vzdalenost<130))
367 kakl 302
                {
371 kakl 303
                    filtr=0;
304
                    if (vzdalenost<55)
367 kakl 305
                    {
371 kakl 306
                        go(M1, 30);
307
                        go(M2, 60);
367 kakl 308
                    }
309
                    else
310
                    {
371 kakl 311
                        go(M1, 60);
312
                        go(M2, 30);
367 kakl 313
                    }
314
                }
315
                else
316
                {
371 kakl 317
                    filtr++;
318
                    if (filtr>5)
319
                    {
377 kakl 320
                        go(M1, 0);  // zastav, neni videt doprovod
321
                        go(M2, 0);
371 kakl 322
                        filtr=6;
323
                    }
367 kakl 324
                };
325
                break;
366 kakl 326
        }
365 kakl 327
    };
366 kakl 328
 
365 kakl 329
	close(file);
330
    pthread_join(thread_1, NULL);
331
    pthread_join(thread_2, NULL);
369 kakl 332
    pthread_join(thread_3, NULL);
365 kakl 333
 
334
	return 0;
335
}
336
 
366 kakl 337
 
365 kakl 338
void *print_tele(void *unused)
339
{
377 kakl 340
    char pom;
366 kakl 341
 
365 kakl 342
    while(true)
343
    {
344
        pRouraI = fopen("/home/ble/pipe","r");
377 kakl 345
        fscanf(pRouraI,"%1s%d", &pom, &param);
365 kakl 346
        fclose(pRouraI);
377 kakl 347
        if (pom!='i') command=pom;
348
 
365 kakl 349
        pRouraO = fopen("/home/ble/pipe","w");
377 kakl 350
        fprintf(pRouraO,"US: %u cm - ",vzdalenost);
367 kakl 351
 
377 kakl 352
        pthread_mutex_lock(&mutex);
353
        fprintf(pRouraO,"%fN %fE - ", nord, east);
354
        fprintf(pRouraO,"Bod:%d - ", last_cross);
355
        fprintf(pRouraO,"Len:%.1f m /", GeoCalc::EllipsoidDistance(nord, east, cros[last_cross].n, cros[last_cross].e));
356
        fprintf(pRouraO,"Az:%.2f Deg - ", GeoCalc::GCAzimuth(nord, east, cros[last_cross].n, cros[last_cross].e));
357
        fprintf(pRouraO,"AzMag: %d (0-255)\n", read_azimut_mag());
358
        pthread_mutex_unlock(&mutex);
367 kakl 359
 
365 kakl 360
        fclose(pRouraO);
361
    }
362
}
363
 
367 kakl 364
void *gps(void *unused)
365
{
366
    FILE *pRS232;
369 kakl 367
    double N, E, pomN, pomE, nn, ee;
367 kakl 368
 
369
    while(true)
370
    {
371 kakl 371
        pRS232 = fopen("/dev/ttyS1","r");
369 kakl 372
        fscanf(pRS232,"$GPGGA,%*f,%lf,N,%lf,E,*", &N, &E); // parser NMEA
371 kakl 373
        fclose(pRS232);
369 kakl 374
        nn=ldiv((long)N,100).quot;   // prepocet DDMM.MM na DD.DD
375
        pomN=(N-nn*100)/60+nn;
376
        ee=ldiv((long)E,100).quot;
377
        pomE=(E-ee*100)/60+ee;
378
        pthread_mutex_lock(&mutex);         // prepis souradnic do sdilenych promennych
377 kakl 379
        nord=pomN; east=pomE;
367 kakl 380
        pthread_mutex_unlock(&mutex);
371 kakl 381
        usleep(800000);                     // NMEA nechodi castejc nez 1x za 1s
367 kakl 382
    }
383
}
384
 
366 kakl 385
/*
365 kakl 386
void *sensors(void *unused)
387
{
388
	char Buf[64];
389
 
390
    while(true)
391
    {
392
        I2C_addr(US_Addr);
393
        Buf[0]=0x0;
394
        Buf[1]=0x51;
395
        write(file, Buf, 2);
396
        usleep(80000);
397
        read(file, Buf, 3);
398
        vzdalenost=(Buf[1]*256+Buf[2]);
399
        usleep(300000);
400
 
401
        I2C_addr(PIC_Addr);
402
        Buf[0]=command;
403
        write(file, Buf, 1);
404
        read(file, Buf, 1);
405
        ble=Buf[0];
406
    }
407
}
366 kakl 408
*/