Страница 1 из 1

как передать по 3-WIRE

Добавлено: Вт мар 02, 2010 19:22:36
alekse1111
Проблема в следующем. Имеется atmega8. Ее первые 3 бита порта С отводятся под 3-WIRE. Есть переменная в 16bit. Эти 16 bit нужно передать по 3-WIRE на ЦАП LTC1655. Да вот что то не получается нужного результата при передаче. Передовал вот так:

bit j,jj,x;
#define CLK PORTC.0
#define DIN PORTC.1
#define CSLD PORTC.2
unsigned int a,row_data,i,temp,data1,temp2,temp3;

char data[4],dat[4];

///////////
кусок кода)
////////////
temp3=data1*21;
CSLD=0;



temp3=temp3>>15; //15
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>14; //14
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>13; //13
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>12; //12
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>11; //11
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>10; //10
x=temp3;
DIN=x;
;
CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>9; //9
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>8; //8
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>7; //7
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>6; //6
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>5; //5
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>4; //4
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>3; //3
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>2; //2
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


temp3=data1*21;
temp3=temp3>>1; //1
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;



temp3=data1*21;
//0
x=temp3;
DIN=x;

CLK=1;
delay_ms(10);
CLK=0;


CSLD=1;
Если у кого есть наработки с 16 DAC прошу выложить.
Еще хочу отметить что при такой реализации 3-wire криво преобразуется сигнал. Моделировал в PROTEUS, может как нить не правильно подключил сам ЦАП.

Добавлено: Вт мар 02, 2010 19:37:46
ARV
во-первых, а почему аппаратный SPI не использовать?
во-вторых, ваша программная реализация вызывает ускоренное выпадение волос, ибо дыбом они встать уже не в силах... вы не в курсе, что повторяющиеся операции надо делать в цикле?

Код: Выделить всё

void clk(char hi){
   if(hi)
      PORDB |= 1;
   else
      PORTB &= ~1;
}

void send_bit(char bit){
   if(bit)
      PORTB |= 2;
   else
      PORTB &= ~2;
}

void send_int(unsigned int data){
   unsigned int mask = 1;
   unsigned int i;
   for(i = 0; i<16;i++){
      clk(1);
      send_bit(data & mask);
      clk(0);
      mask <<= 1;
   }
}
примерно так должно выглядеть - я написал общую суть, в деталях мог сделать не так, как надо - главное, уловите идею.

Добавлено: Вт мар 02, 2010 20:24:07
alekse1111
Циклов не делал, потому как просто проверял, как работает 3-wire.
поправьте если не так:
temp3=data; //те data - данные которые нужно передать
CLK=0;
SCLD=0; - начало передачи
потом передаем старший бит temp3, для этого сдвигаем его на 15 битов вправо(тк данные имеют размер 16 бит),и присваеваем его допустим x (bit x). Далее устанавливаем CLK=1, делаем задержку t и обнуляем СLK.
и таким образом передаем все остальные биты.

Только вот проблемка, при такой передачи DAC не правильно показывает выходное напряжение. МОжет кто нить в PROTEUS скинет модельку правильно подключения DAC(тип ЦАП в первом посту). Буду очень благодарен, потому как голова уже болит от непонимания в чем дело((

Добавлено: Вт мар 02, 2010 20:34:33
ARV
alekse1111 писал(а):Циклов не делал, потому как просто проверял, как работает 3-wire.
поправьте если не так:
temp3=data; //те data - данные которые нужно передать
CLK=0;
SCLD=0; - начало передачи
потом передаем старший бит temp3, для этого сдвигаем его на 15 битов вправо(тк данные имеют размер 16 бит),и присваеваем его допустим x (bit x). Далее устанавливаем CLK=1, делаем задержку t и обнуляем СLK.
и таким образом передаем все остальные биты.

Только вот проблемка, при такой передачи DAC не правильно показывает выходное напряжение. МОжет кто нить в PROTEUS скинет модельку правильно подключения DAC(тип ЦАП в первом посту). Буду очень благодарен, потому как голова уже болит от непонимания в чем дело((
вы обратите внимание на то, что я вам рекомендовал, и сделайте свой алгоритм ПРАВИЛЬНО.

ваша ошибка вот в чем: допустим, у вас число 1011000000000000. что выделаете? сначала сдвигаете его на 15 и получаете 0000000000000001 - все верно. но потом вы хотите передать следующий бит и сдвигаете на 14.... и что получаете? 0000000000000010... это число не равно нулю, и вы снова выдаете в порт 1, а не ноль. ну и так далее.

в моем примере надо сделать mask = 0x8000; в начале и сдвигать ее не влево, а вправо. а начало и конец посылки вы и сами добавить сможете.

Добавлено: Вт мар 02, 2010 20:49:49
alekse1111
Я же написал, что temp3=data, перед каждым последующим сдвигом temp3=data. Так что правильно сдвигаю.(смотрите код в 1 посте). Для меня главное что бы правильно преобразование выполнялось на DAC. И если я добьюсь правильного преобразования data в напряжение, то буду улучшать код.
Ниже выложен код и модель в протеус.
Помогите разобраться плиз....

Добавлено: Ср мар 03, 2010 11:30:51
md5sum
Так тебе уже показали на ошибку :)
1011000000000000.... сдвигаете на 14.... и что получаете? 0000000000000010
Потом ты присваиваешь это число биту! Компилятор за тебя "додумал" и подставил "DIN=(x>0?1:0)" и вместо 0 передалась 1
Маску на число НУЖНО накладывать.

Добавлено: например поправь

Код: Выделить всё

temp3=data1*21;
temp3=temp3>>12; //12
x=temp3;
DIN=x; 
на

Код: Выделить всё

temp3=data1*21;
temp3=temp3>>12; //12
x=temp3&0x01;
DIN=x; 

Добавлено: Сб мар 06, 2010 10:53:39
alekse1111
Интересно, а SPI также работает как и 3-WIRE? Тогда может есть проще способ передать число в 16 bit на DAC? Если можно скиньте пример использования SPI в Codevision. Заранее благодарю

Добавлено: Сб мар 06, 2010 12:51:33
dosikus
Почему бы не сделать софтовую(аппаратную) передачу 1 байта ?
И вызывать передачу сколько влезет ?
Перед передачей 1 байта защелку в 0 , после передачи последнего в 1.
И на хрена сдвигать более чем на 1 ?
Выставляем на выход в зависимости от проверки крайние биты (
какие - 0 или 7 зависит от приемника)-Так же по маске выделяем.
И если 7 двигаем влево , 0 вправо .
И крутим это в цикле 8 раз.



Ясно - вы двигаете маску . Но можно и буфер , все равно в функцию
передается его копия.

Добавлено: Сб мар 06, 2010 22:16:45
alekse1111
Я так понял что spi передает только байт. А как мне одновременно передать 16 бит?

Добавлено: Сб мар 06, 2010 22:26:11
sema
передать два байта :wink: , посмотрите как работает SPI в даташите
одновременно передать 16 бит можно только по параллельной шине разрядностью > 16 бит

Добавлено: Пт мар 12, 2010 17:23:30
alekse1111
Вообще 3-wire и spi это одно и то же?

Re: как передать по 3-WIRE

Добавлено: Сб мар 13, 2010 10:17:45
AI_Disable
В общем случаи, да. Вот у меня какрас функция программного 16-битного SPI завалялась. Может пригодится...

Код: Выделить всё

#define SS 0
#define SCK 1
#define MOSI 3
#define MISO 4
#define PORT_SS PORTB
#define PORT_SCK PORTB
#define PORT_MOSI PORTB
#define PORT_MISO PORTB

unsigned int SPI_TX_RX(unsigned int data){
unsigned int temp=0;
PORT_SCK&=~(1<<SCK);
PORT_SS&=~(1<<SS);
for(unsigned char i=0;i<16;i++)
	{
	if(data&0x8000) PORT_MOSI|=(1<<MOSI);
	else PORT_MOSI&=~(1<<MOSI);
	PORT_SCK|=(1<<SCK);
	temp<<=1;
	if(bit_is_set(PORT_MISO,MISO)) temp|=1;
	PORT_SCK&=~(1<<SCK);
	data<<=1;
	}
PORT_SS|=(1<<SS);
return(temp);
}

Re: как передать по 3-WIRE

Добавлено: Сб мар 13, 2010 14:34:37
ARV
AI_Disable писал(а):В общем случаи, да. Вот у меня какрас функция программного 16-битного SPI завалялась. Может пригодится...
да оно автору и на фиг не надо - я вон давал практически такой же код - и что автор темы ответил? как среагировал? нет никакого желания стараться еще чем-то ему помогать...

Re: как передать по 3-WIRE

Добавлено: Сб мар 13, 2010 15:51:37
dosikus
ARV писал(а):да оно автору и на фиг не надо - я вон давал практически такой же код - и что автор темы ответил? как среагировал? нет никакого желания стараться еще чем-то ему помогать...
Может наконец дошло , что неправ был?!

Re: как передать по 3-WIRE

Добавлено: Чт май 13, 2010 01:24:56
Valeri
Ребят, подскажите такое.
В даташите на чип-контроллер LCD написано 3-WIRE (HT1621) интрефейс связи с такими ногами: /sc , /rd, /wr, data. Как правильно подсоединится к AVR апаратному SPI??? если можна схемку.

спасибо

Re: как передать по 3-WIRE

Добавлено: Чт май 13, 2010 14:37:47
Engineer_Keen
Насколько я понял из описания у HT1621 хоть и 3-wire, но это не совсем SPI, потому как в SPI для такта используется 1 линия, а для данных в разные стороны - 2. У HT1621 - 2 линии для такта (на ввод и на вывод), а для данных одна общая. Если работать в одну сторону (МК->дисплей), то думаю можно просто соединить МК SCL - /wr, MK DO - data, ну и какую-нибудь ногу МК с /CS. А вот если надо читать данные с дисплея, тот тут уже наверно надо городить аппаратный протокол...

Re: как передать по 3-WIRE

Добавлено: Чт май 13, 2010 15:27:59
Valeri
Сейчас попробую. результат опубликую :)) , просто невполне понятно зачем может понадобится читать чтото с 1621. Разве что для контроля(обратной связи). И еще один вопрос. /CS это chip select , а я вроде собираюсь использовать только один чип. может мне эту ногу просто заземлить(ибо инверсный вход) да и пусть 1621 думает что его выбрали. Или ошибаюсь?

Re: как передать по 3-WIRE

Добавлено: Чт май 13, 2010 15:48:17
Engineer_Keen
CS лучше не заземлять, вдруг при запуске какой-нибудь мусор попадет на 1621 и он неизвестно в каком положении окажется. А так процедура записи всегда будет начинаться со сброса приемника и никакой мусор не страшен.

Читать с периферийных устройств, которые казалось бы только для вывода можно много чего, например какой-нибудь статусный регистр. Может оказаться что устройство занято (соответствующий бит в регистре статуса), а вы пытаетесь что-то в него записать. Тут надо внимательнее справочные данные изучить и определить стоит ли чего считывать или нет.