Форум программистов, компьютерный форум, киберфорум
C++ Builder
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.67/6: Рейтинг темы: голосов - 6, средняя оценка - 4.67
5 / 5 / 3
Регистрация: 18.10.2011
Сообщений: 156

Проблема с отправкой нулей.

18.10.2011, 17:00. Показов 1203. Ответов 2
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Все прекрасно работает, только не отправляет нулевые байты.
Помогите чайнику,пожааалуйста!))

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
//----------------------Writing----------------------------------------------
//---------------------------------------------------------------------------
//поток для записи последовательности байтов из буфера в COM-порт
class WriteThread : public TThread
{
private: 
  void __fastcall Printing();  //вывод состояния на экран 
protected: 
        void __fastcall Execute();      //основная функция потока 
public: 
        __fastcall WriteThread(bool CreateSuspended);  //конструктор потока 
}; 
//--------------------------------------------------------------------------- 
//............................... поток WriteThead ............................ 
WriteThread *writer;     //объект потока WriteThread
//--------------------------------------------------------------------------- 
//конструктор потока WriteThread, по умолчанию пустой 
__fastcall WriteThread::WriteThread(bool CreateSuspended) : TThread(CreateSuspended) 
{} 
//---------------------------------------------------------------------------
//главная функция потока, выполняет передачу байтов из буфера в COM-порт
void __fastcall WriteThread::Execute() 
{ 
 DWORD temp, signal;    //temp - переменная-заглушка
 overlappedwr.hEvent = CreateEvent(NULL, true, true, NULL);       //создать событие
 WriteFile(COMport, bufwr, strlen(bufwr), &temp, &overlappedwr);  //записать байты в порт (перекрываемая операция!)
 signal = WaitForSingleObject(overlappedwr.hEvent, INFINITE);     //приостановить поток, пока не завершится перекрываемая операция WriteFile
 if((signal == WAIT_OBJECT_0) && (GetOverlappedResult(COMport, &overlappedwr, &temp, true))) fl = true; //если операция завершилась успешно, установить соответствующий флажок
 else fl = false;
 Synchronize(Printing); //вывести состояние операции в строке состояния
 CloseHandle(overlappedwr.hEvent);  //перед выходом из потока закрыть объект-событие
}
//---------------------------------------------------------------------------
 
//вывод состояния передачи данных на экран
void __fastcall WriteThread::Printing()
{
 if(!fl)  //проверяем состояние флажка 
  {
   Form1->StatusBar1->Panels->Items[0]->Text  = "Ошибка передачи";
   return; 
  }
 Form1->StatusBar1->Panels->Items[0]->Text  = "Передача прошла успешно";
} 
 
//---------------------------------------------------------------------------
//функция открытия и инициализации порта
void COMOpen()
{
 String portname;        //имя порта (например, "COM1", "COM2" и т.д.)
 DCB dcb = {0};                //структура для общей инициализации порта DCB
 COMMTIMEOUTS timeouts;  //структура для установки таймаутов
 portname = Form1->ComboBox1->Text;  //получить имя выбранного порта
 
 //открыть порт, для асинхронных операций обязательно нужно указать флаг FILE_FLAG_OVERLAPPED
 COMport=CreateFile(portname.c_str(),GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING,FILE_FLAG_OVERLAPPED, NULL);
 //здесь:
 // - portname.c_str() - имя порта в качестве имени файла, c_str() преобразует строку типа String в строку в виде массива типа char, иначе функция не примет
 // - GENERIC_READ | GENERIC_WRITE - доступ к порту на чтение/записть
 // - 0 - порт не может быть общедоступным (shared)
 // - NULL - дескриптор порта не наследуется, используется дескриптор безопасности по умолчанию
 // - OPEN_EXISTING - порт должен открываться как уже существующий файл
 // - FILE_FLAG_OVERLAPPED - этот флаг указывает на использование асинхронных операций
 // - NULL - указатель на файл шаблона не используется при работе с портами
 if(COMport == INVALID_HANDLE_VALUE)            //если ошибка открытия порта
  {
   Form1->SpeedButton1->Down = false;           //отжать кнопку
   Form1->StatusBar1->Panels->Items[0]->Text = "Не удалось открыть порт";       //вывести сообщение в строке состояния
   return;
  }
  else Form1->StatusBar1->Panels->Items[0]->Text = "  Порт " + portname+ " открыт успешно";
 
 //инициализация порта
 dcb.DCBlength = sizeof(DCB);   //в первое поле структуры DCB необходимо занести её длину,
                                //она будет использоваться функциями настройки порта
                                //для контроля корректности структуры
 
 //считать структуру DCB из порта
 if(!GetCommState(COMport, &dcb)) //если не удалось - закрыть порт и вывести сообщение об ошибке в строке состояния
  {
   COMClose();
   Form1->StatusBar1->Panels->Items[0]->Text  = "Не удалось считать DCB";
   return;
  }
 
 //инициализация структуры DCB
 dcb.BaudRate = StrToInt(Form1->ComboBox2->Text);       //задаём скорость передачи 115200 бод
 dcb.fBinary = TRUE;                                    //включаем двоичный режим обмена
 dcb.fOutxCtsFlow = FALSE;                              //выключаем режим слежения за сигналом CTS
 dcb.fOutxDsrFlow = FALSE;                              //выключаем режим слежения за сигналом DSR
 dcb.fDtrControl = DTR_CONTROL_DISABLE;                 //отключаем использование линии DTR
 dcb.fDsrSensitivity = FALSE;                           //отключаем восприимчивость драйвера к состоянию линии DSR
 dcb.fNull = FALSE;                                     //разрешить приём нулевых байтов
 dcb.fRtsControl = RTS_CONTROL_DISABLE;                 //отключаем использование линии RTS
 dcb.fAbortOnError = FALSE;                             //отключаем остановку всех операций чтения/записи при ошибке
 dcb.ByteSize = 8;                                      //задаём 8 бит в байте
 dcb.Parity = NOPARITY;                                        //отключаем проверку чётности
 dcb.StopBits = ONESTOPBIT;                                      //задаём один стоп-бит
 dcb.XonChar = TRUE;                                            //Задает символ XON используемый как для примема, так и для передачи.
 dcb.XoffChar = TRUE;                                            //Задает символ XOFF используемый как для примема, так и для передачи.
 //загрузить структуру DCB в порт
 SetCommState(COMport, &dcb);
 if(!SetCommState(COMport, &dcb)) //если не удалось - закрыть порт и вывести сообщение об ошибке в строке состояния
  {
   COMClose();
   Form1->StatusBar1->Panels->Items[0]->Text  = "Не удалось установить DCB";
   return;
  }
 
 //установить таймауты
 timeouts.ReadIntervalTimeout = 20;    //таймаут между двумя символами
 timeouts.ReadTotalTimeoutMultiplier = 1;  //общий таймаут операции чтения
 timeouts.ReadTotalTimeoutConstant = 1;       //константа для общего таймаута операции чтения
 timeouts.WriteTotalTimeoutMultiplier = 100;    //общий таймаут операции записи
 timeouts.WriteTotalTimeoutConstant = 1000;      //константа для общего таймаута операции записи
 
 //записать структуру таймаутов в порт
 SetCommTimeouts(COMport, &timeouts);
 if(!SetCommTimeouts(COMport, &timeouts))  //если не удалось - закрыть порт и вывести сообщение об ошибке в строке состояния
  {
   COMClose();
   Form1->StatusBar1->Panels->Items[0]->Text  = "Не удалось установить тайм-ауты";
   return;
  }
 
//установить размеры очередей приёма и передачи
 SetupComm(COMport,2000,2000);
 
 //создать или открыть существующий файл для записи принимаемых данных
 handle = open("test.txt", O_CREAT | O_APPEND | O_BINARY | O_WRONLY, S_IREAD | S_IWRITE);
 
 if(handle==-1)   //если произошла ошибка открытия файла
  {
   Form1->StatusBar1->Panels->Items[1]->Text = "Ошибка открытия файла";  //вывести сообщение об этом в командной строке
   Form1->Label6->Hide();                                               //спрятать надпись с именем файла
   Form1->CheckBox3->Checked = false;                                   //сбросить и отключить галочку
   Form1->CheckBox3->Enabled = false;
  }
 else { Form1->StatusBar1->Panels->Items[1]->Text = " test.txt открыт"; } //иначе вывести в строке состояния сообщение об успешном открытии файла
 
 PurgeComm(COMport, PURGE_RXCLEAR);  //очистить принимающий буфер порта
 
 reader = new ReadThread(false);   //создать и запустить поток чтения байтов
 reader->FreeOnTerminate = true;   //установить это свойство потока, чтобы он автоматически уничтожался после завершения
 
}
//---------------------------------------------------------------------------
//функция закрытия порта
void COMClose()
{
 //если поток записи работает, завершить его; проверка if(writer) обязательна, иначе возникают ошибки
 if(writer)writer->Terminate();
 //если поток чтения работает, завершить его; проверка if(reader) обязательна, иначе возникают ошибки
 if(reader)reader->Terminate();
 
 CloseHandle(COMport);  //закрыть порт
 COMport=0;     //обнулить переменную для дескриптора порта
 close(handle);     //закрыть файл для записи принимаемых данных
 handle=0;      //обнулить переменную для дескриптора файла
}
//---------------------------------------------------------------------------
вводится двоичное 8-мибитное число в Edit и его нужно отправить через COM порт

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
//----------------------------Меню-побайтовой отправки-----------------------
//---------------------------------------------------------------------------
void __fastcall TForm1::Button5Click(TObject *Sender)
{
 memset(bufwr,0,BUFSIZE);    //очистить программный передающий буфер, чтобы данные не накладывались друг на друга
 PurgeComm(COMport, PURGE_TXCLEAR);             //очистить передающий буфер порта
 AnsiString S,Str="",StrMemo;
 StrMemo=Form1->Edit2->Text.c_str();
 int leng=StrMemo.Length();
 if (leng>0)                                          //Проверка длины строки
 {
        if (leng%8>0)
                for(int i=0; i<(8-(leng%8)); i++)
                        StrMemo+='0';
        int a=0,b=0;
        for(int i=1; i<9; i++)                        //перевод из двоичной в десятичную 8 бит
        {
                S=StrMemo[i];
                a=S.ToInt();
                b+=(a*pow(2,8-i));         //b=b+a*2^(8-i)
        }
        char x = (char)b;                          //конвертирование из бинарной(десятичной) в символьную   
        Str=(AnsiString)(x);                      //x в строковую
        char *y = Str.c_str();               // в char * для буфера
        strcpy(bufwr,y);                     //занести в программный передающий буфер строку из Edit1
        writer = new WriteThread(false);     //создать и активировать поток записи данных в порт
        writer->FreeOnTerminate = true;      //установить это свойство,
                                              //чтобы поток автоматически уничтожался после завершения
        }
}
вобщем нагородил всего, но заработало, только нулевые значения не шлет нифига.
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
18.10.2011, 17:00
Ответы с готовыми решениями:

Затруднения с отправкой переменной по емейлу
Здравствуете! Прошу помочь мне решить две проблемы, а именно. Среда программирования RAD XE8. Есть маленькое приложение. Клик на картинку...

Трудности с отправкой файла по почте
Всем привет! Пишу программу для отправки email-ов, решил добавить в программу функцию прикрепления файлов. (для отправки использую...

Не могу убрать ошибки с отправкой
IdSMTP1-&gt;Host=&quot;mail.rambler.ru&quot;; IdSMTP1-&gt;Username=&quot;z.leonov@rambler.ru&quot;; IdSMTP1-&gt;Password=password; ...

2
 Аватар для radiohobbyt
192 / 190 / 15
Регистрация: 27.01.2009
Сообщений: 548
18.10.2011, 23:25
C
1
WriteFile(COMport, bufwr, strlen(bufwr), &temp, &overlappedwr);  //записать байты в порт (перекрываемая операция!)
тут у тебя bufwr- вроде как строка. а строка считается до первого нуля. соответственно массив из одного нуля имеет длину ноль- ничего и не передается.
1
5 / 5 / 3
Регистрация: 18.10.2011
Сообщений: 156
19.10.2011, 13:17  [ТС]
А как сделать правильно?

Добавлено через 1 час 7 минут
Решил, ставя длину во WriteFile равной единице, если нулевой байт.
А можно сделать как-нибудь по нормальнее?
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
19.10.2011, 13:17
Помогаю со студенческими работами здесь

Проблема с отправкой почты
Не могу передать почту в общем,в инете масса тем по этому поводу,но не получается все равно string...

Проблема С Отправкой E-mail
Итак, исходные... имеется Lotus 8.5, HP Service Desk (черт его знает, какой версии) и агент, посылающий заявки из Лотуса. &lt;div...

Проблема с отправкой почты по SMTP
не пойму, как произвести аутентификацию перед отправкой почты по СМТП протоколу. Во всех стандартных примерах, которые находил, даже пароль...

Outlook Express 6 проблема с отправкой.
Всем привет! Подскажите пожалуйста в чём проблема. Оутлук не хочет отправлять письма пишет ошибку (в прикреплённом файле). У меня два ящика...

Проблема с отправкой по USART STM32F3
Добрый вечер, никак не могу найти ошибку в коде для отправки данных с микроконтроллера на ПК с помощью USORT и блютуз HC-06. STM32F303VC...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
3
Ответ Создать тему
Новые блоги и статьи
SDL3 для Desktop (MinGW): Создаём пустое окно с нуля для 2D-графики на SDL3, Си и C++
8Observer8 10.03.2026
Содержание блога Финальные проекты на Си и на C++: hello-sdl3-c. zip hello-sdl3-cpp. zip Результат:
Установка CMake и MinGW 13.1 для сборки С и C++ приложений из консоли и из Qt Creator в EXE
8Observer8 10.03.2026
Содержание блога MinGW - это коллекция инструментов для сборки приложений в EXE. CMake - это система сборки приложений. Здесь описаны базовые шаги для старта программирования с помощью CMake и. . .
Как дизайн сайта влияет на конверсию: 7 решений, которые реально повышают заявки
Neotwalker 08.03.2026
Многие до сих пор воспринимают дизайн сайта как “красивую оболочку”. На практике всё иначе: дизайн напрямую влияет на то, оставит человек заявку или уйдёт через несколько секунд. Даже если у вас. . .
Модульная разработка через nuget packages
DevAlt 07.03.2026
Сложившийся в . Net-среде способ разработки чаще всего предполагает монорепозиторий в котором находятся все исходники. При создании нового решения, мы просто добавляем нужные проекты и имеем. . .
Модульный подход на примере F#
DevAlt 06.03.2026
В блоге дяди Боба наткнулся на такое определение: В этой книге («Подход, основанный на вариантах использования») Ивар утверждает, что архитектура программного обеспечения — это структуры,. . .
Управление камерой с помощью скрипта OrbitControls.js на Three.js: Вращение, зум и панорамирование
8Observer8 05.03.2026
Содержание блога Финальная демка в браузере работает на Desktop и мобильных браузерах. Итоговый код: orbit-controls-threejs-js. zip. Сканируйте QR-код на мобильном. Вращайте камеру одним пальцем,. . .
SDL3 для Web (WebAssembly): Синхронизация спрайтов SDL3 и тел Box2D
8Observer8 04.03.2026
Содержание блога Финальная демка в браузере. Итоговый код: finish-sync-physics-sprites-sdl3-c. zip На первой гифке отладочные линии отключены, а на второй включены:. . .
SDL3 для Web (WebAssembly): Идентификация объектов на Box2D v3 - использование userData и событий коллизий
8Observer8 02.03.2026
Содержание блога Финальная демка в браузере. Итоговый код: finish-collision-events-sdl3-c. zip Сканируйте QR-код на мобильном и вы увидите, что появится джойстик для управления главным героем. . . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru