यह आईपी केवीएम थीम पर तीसरा बदलाव है, इस बार की अवधारणा को पूरी तरह से संशोधित किया गया है, चलो कुछ नया बनाना शुरू करते हैं। कई दिलचस्प चीजें होंगी, स्क्रीन को मत छोड़ो। एक और असामान्य उपकरण दिखाई देगा, हम लगभग सभी पुराने घटकों को छोड़ देंगे, अपने मूल arduino में वापस जाएंगे और थोड़ा हैकर खेलेंगे।
उन लोगों के लिए जो अभी-अभी जुड़े हैं, पिछले एपिसोड का सारांश:
- पहला लेख
Arduino और रास्पबेरी पाई पर आईपी केवीएम एकत्र, यह महंगा और खराब वीडियो गुणवत्ता के साथ निकला। - दूसरा लेख
OrangePI और Atmega16u2, सस्ते में सीखे, लेकिन छवि गुणवत्ता अभी भी घृणित है।
और अंत में, इस लेख में, पिछले वाले सभी नुकसान तय किए जाएंगे। घटकों की लागत में अधिकतम कमी पर विशेष रूप से जोर दिया जाएगा।
परंपरा से, हम असेंबल किए गए डिवाइस के घटकों पर विचार करते हैं:1. हमारे पुराने दोस्त Atmega16u2:
यह एकमात्र घटक है जो पिछले लेखों से आगे बढ़ेगा।
2. कुख्यात ESP8266, इस मामले में ESP8266-12e:
आप ईएसपी 8266 के दूसरे संस्करण का उपयोग कर सकते हैं, केवल आपको बंदरगाहों की संख्या और स्थान पर विचार करने की आवश्यकता है।
3. और, वास्तव में, अवसर LKV373A के नायक

इस उपकरण के लिए धन्यवाद, उच्च के साथ एक स्थानीय नेटवर्क पर वीडियो प्रसारित करना संभव हो गया
फुल-एचडी तक रिज़ॉल्यूशन।
कार्य योजना इस प्रकार है:
- छिपाएँ और तलाश करें: हम LKV373A की तलाश कर रहे हैं, जहाँ वह किस आईपी पते के तहत नेटवर्क पर छिपा है
- हैकर गेम: फर्मवेयर भरें, पासवर्ड रीसेट करें और LKV373A कॉन्फ़िगर करें
- नए दोस्त बनाना: ESP8266, Arduino IDE और मज़ेदार तस्वीरें
- उत्सव का समापन। हम सभी घटकों को जोड़ते हैं और टेलनेट के माध्यम से कीस्ट्रोक्स संचारित करते हैं
LKV373A पृष्ठभूमि
तो चलिए शुरू करते है! LKV373A या एचडीएमआई एक्सटेंडर डिवाइस को hdmi पोर्ट से सीधे इमेज कैप्चर करने और स्थानीय नेटवर्क पर प्रसारित करने के लिए, इन डिवाइसों को hdmi extenders भी कहा जाता है। जैसा कि निर्माताओं ने योजना बनाई है, ऐसे उपकरणों के एक सेट में क्रमशः एक ट्रांसमीटर (ट्रांसमीटर) और रिसीवर (रिसीवर), पदनाम TX और RX शामिल होना चाहिए। उन्हें केवल जोड़े में निर्माता को अधिक लाभ लाने के लिए, शायद, उपयोग किया जाना चाहिए। लेकिन डैनमैन उपनाम के तहत एक आदमी था, यहां उनके ब्लॉग की एक
कड़ी है, जो इस बात में रुचि रखते थे कि यह कैसे काम करता है। उन्होंने विंडसरक खोला, TX डिवाइस द्वारा प्रेषित ट्रैफ़िक को सूँघा, क्या निकला?
वीडियो स्ट्रीम किसी भी एन्क्रिप्शन के बिना प्रसारित की जाती है, और वीएलसी प्लेयर का उपयोग करके, आप इसे बहुत अधिक प्रयास के बिना देख सकते हैं। लेकिन वह वहां नहीं रुका, "महसूस किया": उसने वेब इंटरफेस, टीटीएल, टेलनेट, और यहां तक कि फर्मवेयर को प्रोग्रामर के साथ खींच लिया। उन्होंने अपने ब्लॉग पर इस बारे में विस्तार से बात की। फर्मवेयर जो हमें सबसे पहले रुचता है, उसे भी वहां अपलोड किया गया था: IPTV_TX_PKG_v4_0_0_0_20160427.PKG। इस फर्मवेयर में, उन्नत सेटिंग्स वाला वेब इंटरफ़ेस, और मानक एक जैसा नहीं, केवल अपडेट बटन है। इसके अलावा, इस फर्मवेयर में कॉन्फ़िगर करने के लिए कई कमांड के साथ एक टेलनेट है। यह इस फर्मवेयर के साथ है कि हम अपने कार्यों के लिए एचडीएमआई एक्सटेंडर को फिर से कॉन्फ़िगर करें। मैंने फर्मवेयर और सब कुछ जिसकी मुझे जरूरत थी, जीथब पर पोस्ट किया, यहां
लिंक है , हमें बाद में इसकी आवश्यकता होगी, लेकिन अब हम सिद्धांत के साथ समाप्त करते हैं। अभ्यास के लिए आगे बढ़ते हैं।
ट्रांसमीटर
नेट पर LKV373A की तलाश है
मैं उसी एक्सटेंडर के हाथों में गिर गया, जैसे डैनमैन (y)। नीचे वर्णित सभी विशेष रूप से एचडीएमआई एक्सटेंडर LKV373A संस्करण V3.0 के लिए उपयुक्त है!
हम LKV373A को स्थानीय नेटवर्क से जोड़ते हैं, बिजली चालू करते हैं। अब यह सुनिश्चित करने का प्रयास करें कि डिवाइस
ping 192.168.1.238
नेटवर्क पर दिखाई दे।
192.168.1.238 डिफ़ॉल्ट IP पता है। यदि एक्सटेंडर पुराने फर्मवेयर एड्रेस को नहीं बदलता है, तो इस बात की परवाह किए बिना कि नेटवर्क पर डीएचसीपी सर्वर है या नहीं। नए फर्मवेयर संस्करण केवल डिफ़ॉल्ट रूप से आईपी का उपयोग करते हैं यदि डिवाइस डीएचसीपी से पता प्राप्त करने में असमर्थ था। यदि आपको पिंग की प्रतिक्रिया मिली, तो जारी रखें। यदि नहीं, तो निराशा न करें, एक्सटेंडर को सीधे कंप्यूटर के लैन पोर्ट से जोड़ने का प्रयास करें और स्निफर का उपयोग करें।
सिलाई
एचडीएमआई एक्सटेंडर मिला, फर्मवेयर पर आगे बढ़ें।
चलो गितुब पर जाएं और वहां रखी हर चीज को डाउनलोड करें। अब एक ब्राउज़र के माध्यम से एक्सटेंडर के वेब इंटरफेस को खोलें और निम्न चित्र देखें:

"ब्राउज़ करें ..." पर क्लिक करें, फ़र्मवेयर चुनें, IPTV_TX_PKG_v4_0_0_0_20160427.PKG नामक एक फ़ाइल, और "अपग्रेड" पर क्लिक करें। Tadam! फर्मवेयर पूरा हो गया है, अब पासवर्ड रीसेट करने के लिए टेलनेट द्वारा LKV373A से कनेक्ट करें।
कनेक्ट करने का कमांड टेलनेट 192.168.1.238 9999 जैसा कुछ दिखाई देगा, जहां 9999 को कनेक्ट करने के लिए पोर्ट है। सीईपी चेतावनी देता है: डीएचसीपी से प्राप्त पता एक नेटवर्क स्कैनर का उपयोग करके पाया जा सकता है।
टेलनेट के माध्यम से कनेक्ट करें
कनेक्ट करते समय, निम्न संदेश दिखाई देना चाहिए:
============================== ========IPTV TX Server======== ============================== input>
हम
list
लिखते हैं। जवाब में, हमें आदेशों की एक सूची मिलती है:
============================== ========IPTV TX Server======== ============================== input>list set_group_id get_group_id set_dhcp get_dhcp set_uart_baudrate get_uart_baudrate set_static_ip get_static_ip set_mac_address get_mac_address get_lan_status get_hdcp get_video_lock get_ip_config set_session_key set_device_name get_device_name set_video_bitrate get_video_bitrate set_downscale_mode get_downscale_mode set_video_out_mode get_video_out_mode set_streaming_mode get_streaming_mode get_fw_version get_company_id factory_reset reboot list exit
सभी सेटिंग्स और पासवर्ड रीसेट करने के लिए,
factory_reset
कमांड का उपयोग करें। हम एक कमांड लिखते हैं, एंटर दबाएं और इस तस्वीर को प्राप्त करें:
input>factory_reset Processing factory reset! System will reboot after few seconds! Connection closed by foreign host.
वेब इंटरफ़ेस
अब हम डिवाइस को आवश्यकतानुसार कॉन्फ़िगर कर सकते हैं। आइए वेब इंटरफेस पर जाएं। हम मानक लॉगिन का उपयोग करते हैं: व्यवस्थापक पासवर्ड: 123456 और यहां यह है, अतिरिक्त सेटिंग्स के साथ "प्रतिष्ठित" वेब इंटरफ़ेस:

हालाँकि वेब इंटरफ़ेस में अवसर बढ़ गए हैं, लेकिन वे अभी भी हमारे उद्देश्यों के लिए पर्याप्त नहीं हैं। विशेष रूप से कमी स्ट्रीमिंग के संदर्भ में अधिक निशुल्क सेटिंग्स हैं, यह हार्ड-कोडित है, सबसे सुविधाजनक से दूर, आईपी पते की एक सूची है जिसमें आप स्ट्रीम कर सकते हैं। बेशक एक मल्टीकास्ट है, लेकिन टेलीविजन के लिए इसे छोड़ना बेहतर है। सीमाओं को दरकिनार किया जा सकता है, उस पर और बाद में।
इसलिए, उन्होंने डिवाइस को नेटवर्क पर पाया, इसे रोल किया, पासवर्ड रीसेट किया। ट्रांसमीटर रिसीवर को स्थानांतरित करने के लिए लगभग तैयार है।
रिसीवर
आइए डिवाइस पर निर्णय लेते हैं कि किस ऑपरेटिंग सिस्टम के नियंत्रण में हम धारा प्रवाहित करेंगे। मुझे नहीं लगता कि आपको पसंद की पीड़ा का अनुभव होगा, केवल दो विकल्प हैं:
विंडोज
विंडोज के लिए, मैंने कई खिलाड़ियों की कोशिश की, लेकिन परिणाम बहुत सारे थे। वीडियो स्ट्रीम को कैप्चर करने और फिर चलाने पर, एक विलंब दिखाई देता है, जो मुख्य रूप से स्ट्रीम खेलने वाले खिलाड़ी पर निर्भर करता है। विभिन्न खिलाड़ियों पर, देरी एक सेकंड से लेकर पांच या अधिक तक थी। सबसे अच्छा, विंडोज पर, वीएलसी प्लेयर साबित हुआ।
चलो व्यापार के लिए नीचे उतरो। "मीडिया" ड्रॉप-डाउन मेनू में ऊपर से VLC प्लेयर लॉन्च करें, नेटवर्क एड्रेस फ़ील्ड में "ओपन URL ..." चुनें,
udp://@:5004
लिखें
udp://@:5004
, "एडवांस्ड सेटिंग्स दिखाएं" चेकबॉक्स में एक डाउट डालें और "कैशिंग" फ़ील्ड में अपना मान डालें। यह पैरामीटर व्यक्तिगत रूप से निर्धारित किया जाता है। इस क्षेत्र में मूल्य जितना छोटा होगा, देरी उतनी ही कम होगी, लेकिन बहुत कम मूल्य "कलाकृतियों" और फ्रेम ड्रॉप हो सकता है, सब कुछ स्थानीय नेटवर्क के बुनियादी ढांचे पर निर्भर करेगा। सबसे अच्छा परिणाम जो मैं प्राप्त कर सकता था वह लगभग एक सेकंड की देरी थी। लिनक्स पर, परिणाम 200-300 मिलीसेकंड के आसपास बेहतर थे।
लिनक्स
जैसा कि अभ्यास से पता चलता है, सबसे अच्छा परिणाम सामाजिक और मेलर कार्यक्रमों के संयोजन का उपयोग करके प्राप्त किया जाता है। मेरे कंप्यूटर पर उबंटू स्थापित है, इसलिए सोसाइटी स्थापित करने की कमांड इस तरह दिखाई देगी:
sudo apt-get install socat
Mplayer समान रूप से स्थापित किया गया है:
sudo apt-get install mplayer
खैर, और डैनमैन की सलाह का पालन करें:
sudo iptables -t raw -A PREROUTING -p udp -m length --length 28 -j DROP
तथाकथित "ज़ीरो लेंथ यूडीपी पैकेट्स" को स्ट्रीम से हटाने के लिए इस कमांड की ज़रूरत होती है - स्ट्रीम के पैकेट जो कि "clog" हो।
जाओ जी!
रिसीवर तैयार है, आप प्रसारण शुरू कर सकते हैं! हम ऑपरेटिंग सिस्टम के आधार पर, कंप्यूटर से प्राप्त कंप्यूटर
ifconfig
या
ipconfig
के कंसोल में टाइप करते हैं, हम रिसीवर के आईपी पते को याद करते हैं और ट्रांसमीटर के वेब इंटरफेस पर वापस लौटते हैं। हम वेब इंटरफ़ेस खोलेंगे, यदि हम इसे पहले ही बंद कर चुके हैं, तो उपयोगकर्ता नाम, पासवर्ड दर्ज करें और सीधे ब्राउज़र के एड्रेस बार में लिखें:
http:
अपने आईपी पते को सब्स्टीट्यूट करें और एंटर दबाएं। यह लाइन एचडीएमआई एक्सटेंडर को आपके चुने हुए आईपी पर कब्जा किए गए वीडियो को प्रसारित करने और मल्टीकास्ट को बंद करने के लिए कॉन्फ़िगर करेगी।
हम विंडोज में VLC शुरू करते हैं। या लिनक्स टर्मिनल में हम लिखते हैं:
socat UDP-RECV:5004 - | mplayer –
अब्राहम कैदबरा! और यहाँ हमारा है, या हमारा नहीं है, लाइव डेस्कटॉप।

इसलिए, कुछ हैकर विधियों के साथ, हमने डिवाइस को वह करने के लिए मजबूर किया, जिसकी हमें आवश्यकता थी।
वीडियो को स्थानांतरित करने के साथ, रिमोट कंट्रोल पर जाएं।
नियंत्रण स्थानांतरण
घटक चयन
क्योंकि एचडीएमआई एक्सटेंडर की लागत कम है, लगभग 1800 रूबल, और यह भी कि टिप्पणियों के कारण, वे कहते हैं, थोड़ा महंगा है, मैंने नारा लगाया: "2000 रूबल के लिए आईपी केवीएम दें!"। रूबल की विनिमय दर इस कथन की निष्ठा को बहुत प्रभावित करेगी, लेकिन दुखी चीजों के बारे में बात नहीं करते, मैं उज्ज्वल भविष्य में विश्वास करना चाहता हूं। लक्ष्य को प्राप्त करने के लिए, हमें बहुत सस्ते तत्वों की आवश्यकता होगी, मेरी पसंद एक नियंत्रक के रूप में ईएसपी 8266 पर गिर गई, और सभी एटेमेगा (8/16/32) यू 2 एक एक्ट्यूएटर के रूप में।
आप निश्चित रूप से एक कार्यकारी उपकरण (कीबोर्ड) की भूमिका के लिए अन्य उम्मीदवारों पर विचार कर सकते हैं। कीबोर्ड का अनुकरण करने वाला फर्मवेयर LUFA लाइब्रेरी (सॉर्ट) में लिखा गया है। इस लाइब्रेरी का उपयोग USB कनेक्टिविटी के साथ पूरे AVR परिवार के लिए किया जा सकता है। यह इस प्रकार है कि कीबोर्ड एमुलेटर के रूप में, आप संभवतः सस्ता, माइक्रोकंट्रोलर उठा सकते हैं। यह विचार के लिए जानकारी है, लेकिन अब हम जारी रखते हैं।
आप लगभग 90 रूबल के लिए ESP8266, लगभग 100 रूबल के लिए Atmega (8/16/32) u2 खरीद सकते हैं, और यदि आप 5 के छोटे बैचों, या अधिक टुकड़ों में लेते हैं, तो भी सस्ता है। बेशक, माइक्रोकंट्रोलर्स को स्ट्रैप करने के लिए उपभोग्य सामग्रियों की आवश्यकता होगी, लेकिन उनकी लागत बहुत कम है, इसलिए मैं उन पर विचार नहीं करूंगा।
ESP8266
चीनी उद्योग के इस चमत्कार को किसी परिचय की आवश्यकता नहीं है, इसलिए मैं केवल यह कहूंगा कि इस परियोजना में मैंने ESP8266-12e के संस्करण का उपयोग किया। बेशक, आप अन्य संस्करणों का उपयोग कर सकते हैं, केवल आपको बंदरगाहों के स्थान पर विचार करने की आवश्यकता है, क्योंकि इस संस्करण में, ESP8266 बंदरगाहों में से एक को Atmega (8/16/32) u2 पर बिजली देने के लिए उपयोग किया जाता है, यह नीचे दिए गए आरेख में इंगित किया जाएगा।
प्रविष्टि
ESP8266 के लिए फर्मवेयर ArduinoIDE वातावरण में लिखा गया है, तो चलो
डेवलपर की साइट से नवीनतम संस्करण डाउनलोड करें। अगला आपको ईएसपी 8266 के लिए समर्थन जोड़ने की आवश्यकता है - इस
लिंक पर सबसे आसान तरीका पाया जा सकता है। उसी पृष्ठ पर आप बहुत सारी उपयोगी जानकारी पा सकते हैं, उदाहरण के लिए, बिजली कनेक्शन और टीटीएल की योजना। जो लोग अप टू डेट नहीं हैं, उनके लिए ESP8266
सख्ती से 3.3 वोल्ट का उपयोग करता है
! यदि आप अपनी क्षमताओं में विश्वास नहीं करते हैं, तो USB के लिए अनुकूलित बोर्ड विकल्प का उपयोग करना बेहतर है, जैसे कि NodeMC.U:

यदि सब कुछ तैयार है, तो ArduinoIDE खोलें और मेरा स्केच कॉपी करें:
स्केच #include <ESP8266WiFi.h> #include <WiFiClient.h> #include <ESP8266WebServer.h> #include <ESP8266mDNS.h> #include <SoftwareSerial.h> #include <HIDKeyboard.h> #define MAX_SRV_CLIENTS 3 HIDKeyboard keyboard; const char* host = "esp8266"; const char* ssid = ""; const char* pass = ""; int rebootdev = 0; int modeswitch = 0; // , ESP8266 #define Port1 15 #define Port2 14 #define Port3 12 #define Port4 4 #define Port5 5 // String ColorB1; String ColorB2; String ColorB3; String ColorB4; String ColorB5; ESP8266WebServer server(80); WiFiClient serverClients[MAX_SRV_CLIENTS]; const char* serverIndex = "<form method='POST' action='/update' enctype='multipart/form-data'><input type='file' name='update'><input type='submit' value='Update'></form><a href='/'>BACK</a>";//Update // void handleRedirect(){ String content = "<html><head><meta http-equiv='refresh' content='0;/'><head></html>"; server.send(200, "text/html", content); } // WI-FI void handleLogin(){ String msg = ""; if (server.hasArg("SSID") && server.hasArg("PASSAP")){ if ((server.arg("SSID") != NULL) && (server.arg("PASSAP") != NULL)){ String header = "HTTP/1.1 301 OK\r\r\nLocation: /\r\nCache-Control: no-cache\r\n\r\n"; server.sendContent(header); String web_ssid = server.arg("SSID"); String web_pass = server.arg("PASSAP"); ssid = web_ssid.c_str();// C pass = web_pass.c_str(); Serial.println(); Serial.print("SSID "); Serial.println(ssid); Serial.print("Pass "); Serial.println(pass); WiFi.begin(ssid, pass); digitalWrite(LED_BUILTIN, LOW); ESP.reset(); return; } msg = "Wrong ssid/password! try again."; Serial.println("Login Failed"); } String content = "<html><body><form action='/' method='POST'>Enter the access point name and password <br>";// SSID content += "Name AP:<input type='text' name='SSID' placeholder='SSID'><br>"; content += "Password:<input type='password' name='PASSAP' placeholder='password'><br><br>"; content += "<input type='submit' name='SUBMIT' value='Connect to WI-FI'></form><b><font color='red'>" + msg + "</font></b><br>"; content += "Firmware update <a href='/upload'>UPDATE</a></body></html>"; server.send(200, "text/html", content); } void handleNotFound(){ String message = "File Not Found\n\n"; message += "URI: "; message += server.uri(); message += "\nMethod: "; message += (server.method() == HTTP_GET)?"GET":"POST"; message += "\nArguments: "; message += server.args(); message += "\n"; for (uint8_t i=0; i<server.args(); i++){ message += " " + server.argName(i) + ": " + server.arg(i) + "\n"; } server.send(404, "text/plain", message); } // int controlPin(int UsePin){ if (UsePin > 0){ int StPort; if (digitalRead(UsePin) == 1) {// digitalWrite(UsePin, LOW); StPort = 0; } else { digitalWrite(UsePin, HIGH); StPort = 1; } digitalWrite(LED_BUILTIN, HIGH);// Serial.print("Port "); Serial.print(UsePin); Serial.print("="); Serial.println(StPort); delay(500); digitalWrite(LED_BUILTIN, LOW); return(StPort); } return(-1); } // int clientConnect(int Seconds){ Serial.print("connection "); for (int i=0; i <= Seconds; i++){ WiFi.begin(ssid, pass); digitalWrite(LED_BUILTIN, LOW); delay(250); digitalWrite(LED_BUILTIN, HIGH); delay(250); Serial.print(" "); Serial.print("."); if (WiFi.status() == WL_CONNECTED) return(0); } return(1); Serial.println(); } void setup(void){ Serial.begin(115200); delay(1000); pinMode(LED_BUILTIN, OUTPUT); digitalWrite(LED_BUILTIN, HIGH); //uint8_t i = 0; if (modeswitch == 0) WiFi.mode(WIFI_STA);// modeswitch = 0 Serial.println(); Serial.println(); if (clientConnect(30) != 0) modeswitch = 1;// if (modeswitch == 1){ Serial.println(""); Serial.println("WiFi switch AP mode"); //WiFi.mode(WIFI_AP_STA); + . WiFi.mode(WIFI_AP); WiFi.softAP("TD", "testtest"); Serial.print("AP mode ip adress "); Serial.println(WiFi.softAPIP()); digitalWrite(LED_BUILTIN, LOW); } if (modeswitch != 1){ WiFiServer server(23); Serial.println(); Serial.print("Client mod ip address: "); Serial.println(WiFi.localIP()); digitalWrite(LED_BUILTIN, LOW); } MDNS.begin(host); pinMode(Port1, OUTPUT); pinMode(Port2, OUTPUT); pinMode(Port3, OUTPUT); pinMode(Port4, OUTPUT); pinMode(Port5, OUTPUT); if (modeswitch == 1){ // server.on("/", handleLogin);// (SSID) // server.on("/upload", HTTP_GET, [](){ server.sendHeader("Connection", "close"); server.send(200, "text/html", serverIndex); }); server.on("/update", HTTP_POST, [](){ server.sendHeader("Connection", "close"); int uperror = Update.hasError(); Serial.printf("UPERR %u\nRebooting...\n",Update.hasError()); if (uperror == 0) server.send(200, "text/html", "Firmware update successfully <a href='/'>BACK</a>"); else server.send(200, "text/html", "Update error <a href='/'>BACK</a>"); ESP.restart(); },[](){ HTTPUpload& upload = server.upload(); if(upload.status == UPLOAD_FILE_START){ Serial.setDebugOutput(true); WiFiUDP::stopAll(); Serial.printf("Update: %s\n", upload.filename.c_str()); if (upload.filename == NULL) { Serial.printf("ERROR: zero file size"); server.send(200, "text/html", "<html> zero file size <a href='/upload'>BACK</a></html>"); return(-1); } uint32_t maxSketchSpace = (ESP.getFreeSketchSpace() - 0x1000) & 0xFFFFF000; if(!Update.begin(maxSketchSpace)){//start with max available size Update.printError(Serial); } } else if(upload.status == UPLOAD_FILE_WRITE){ if(Update.write(upload.buf, upload.currentSize) != upload.currentSize){ Update.printError(Serial); } } else if(upload.status == UPLOAD_FILE_END){ if(Update.end(true)){ //true to set the size to the current progress Serial.printf("Update Success: %u\nRebooting...\n", upload.totalSize); } else { Update.printError(Serial); } Serial.setDebugOutput(false); } yield(); }); // server.on("/PoRt1", [] { controlPin(Port1); handleRedirect();// }); server.on("/PoRt2", [] { controlPin(Port2); handleRedirect(); }); server.on("/PoRt3", [] { controlPin(Port3); handleRedirect(); }); server.on("/PoRt4", [] { controlPin(Port4); handleRedirect(); }); server.on("/PoRt5", [] { controlPin(Port5); handleRedirect(); }); server.on("/reboot", [] { rebootdev = 1;// handleRedirect(); }); server.onNotFound(handleNotFound);// //server.begin(); MDNS.addService("http", "tcp", 80); Serial.println(); Serial.println("HTTP server started"); } server.begin(); } void loop(void){ uint8_t i; if (modeswitch == 1) server.handleClient(); delay(100); if (modeswitch != 1){ if (WiFi.status() != WL_CONNECTED) clientConnect(30); else { digitalWrite(5, HIGH);// ATMEGA16U2 digitalWrite(LED_BUILTIN, LOW); } } WiFiServer server(23); server.setNoDelay(true); server.begin(); keyboard.begin(); while(WiFi.status() == WL_CONNECTED) { if (server.hasClient()){ for(i = 0; i < MAX_SRV_CLIENTS; i++){ //find free/disconnected spot if (!serverClients[i] || !serverClients[i].connected()){ if(serverClients[i]) serverClients[i].stop(); serverClients[i] = server.available(); Serial.println("New client: "); Serial.print(i); continue; } } //no free/disconnected spot so reject WiFiClient serverClient = server.available(); serverClient.stop(); } //check clients for data for(i = 0; i < MAX_SRV_CLIENTS; i++){ if (serverClients[i] && serverClients[i].connected()){ if(serverClients[i].available()){ //get data from the telnet client and push it to the UART String bufkey; while(serverClients[i].available()) bufkey += (serverClients[i].read());// if (bufkey != 0) { bufkey = bufkey.substring(0, 8);// int key = bufkey.toInt();// switch (key){ case 277980: keyboard.pressSpecialKey(F1); break; case 277981: keyboard.pressSpecialKey(F2); break; case 277982: keyboard.pressSpecialKey(F3); break; case 277983: keyboard.pressSpecialKey(F4); break; case 27914953: keyboard.pressSpecialKey(F5); break; case 27914955: keyboard.pressSpecialKey(F6); break; case 27914956: keyboard.pressSpecialKey(F7); break; case 27914957: keyboard.pressSpecialKey(F8); break; case 27915048: keyboard.pressSpecialKey(F9); break; case 27915049: keyboard.pressSpecialKey(F10); break; case 27915051: keyboard.pressSpecialKey(F11); break; case 27915052: keyboard.pressSpecialKey(F12); break; case 1310: keyboard.pressSpecialKey(ENTER); break; case 130: keyboard.pressSpecialKey(ENTER); break; case 27: keyboard.pressSpecialKey(ESCAPE); break; case 8: keyboard.pressSpecialKey(BACKSPACE); break; case 9: keyboard.pressSpecialKey(TAB); break; case 32: keyboard.pressSpecialKey(SPACEBAR); break; case 27915012: keyboard.pressSpecialKey(INSERT); break; case 27914912: keyboard.pressSpecialKey(HOME); break; case 27915312: keyboard.pressSpecialKey(PAGEUP); break; case 27915212: keyboard.pressSpecialKey(END); break; case 27915412: keyboard.pressSpecialKey(PAGEDOWN); break; case 279167: keyboard.pressSpecialKey(RIGHTARROW); break; case 279168: keyboard.pressSpecialKey(LEFTARROW); break; case 279166: keyboard.pressSpecialKey(DOWNARROW); break; case 279165: keyboard.pressSpecialKey(UPARROW); break; case 127: keyboard.pressSpecialKey(DELETE); break; case 27915112: keyboard.pressSpecialKey(DELETE); break; case 4: keyboard.pressSpecialKey((LCTRL | ALT), DELETE); break; //CTRL+ALT+DELETE Ctrl + d case 6: keyboard.pressSpecialKey(ALT, F4); break; //alt+f4 Ctrl + f case 19: keyboard.pressSpecialKey(ALT | SHIFT); break;// Ctrl+s case 2: keyboard.pressSpecialKey(LCTRL | SHIFT); break;// Ctrl+b // case 17: controlPin(Port1); break;//Ctrl+q case 23: controlPin(Port2); break;//Ctrl+w case 5: controlPin(Port3); break;//Ctrl+e case 18: controlPin(Port4); break;//Ctrl+r case 20: controlPin(Port5); break;//Ctrl+t default: keyboard.pressKey(key); break;// } keyboard.releaseKey();// Serial.print(" string: "); Serial.print(key);// Serial.print(" KEY: "); Serial.write(bufkey.toInt()); bufkey = '0';// } } } } //check UART for data if(Serial.available()){ size_t len = Serial.available(); uint8_t sbuf[len]; Serial.readBytes(sbuf, len); //push UART data to all connected telnet clients for(i = 0; i < MAX_SRV_CLIENTS; i++){ if (serverClients[i] && serverClients[i].connected()){ serverClients[i].write(sbuf, len); delay(1); } } } } }
वांछित पुस्तकालय कनेक्ट करें:
"स्केच" टैब → "लाइब्रेरी कनेक्ट करें" → ".ZIP लाइब्रेरी जोड़ें" का चयन करें। "UNO-HIDKeyboard-Library-master (mod) .zip" नामक लाइब्रेरी का चयन करें, जिसे github से डाउनलोड किया गया था। हम फर्मवेयर में संकलन और भरते हैं। फर्मवेयर को डाउनलोड करने के लिए, ESP8266 TTL को कनेक्ट करें, ArduinoIDE में वांछित पोर्ट सेट करें। सेटिंग्स कुछ इस तरह दिखना चाहिए:

फर्मवेयर को डाउनलोड करने के लिए, आपको जमीन पर GPIO0 पोर्ट को शॉर्ट-सर्किट करने की आवश्यकता है, और रीसेट पोर्ट को शॉर्ट-सर्कुलेट करके माइक्रोकंट्रोलर को फिर से जमीन पर भेजना होगा। मैं विस्तार से पेंट नहीं करूंगा, इसलिए लेख को नहीं बढ़ाना, Google आपकी मदद करेगा।
ESP8266 का तर्क इस प्रकार है: जब बिजली लागू होती है, तो माइक्रोकंट्रोलर लगभग तीस सेकंड के लिए वाई-फाई एक्सेस प्वाइंट से कनेक्ट करने का प्रयास करता है:
यदि कनेक्शन सफल होता है : पोर्ट 23 को खोलता है, जिसे आप टेलनेट का उपयोग करके कनेक्ट कर सकते हैं और कीस्ट्रोक्स संचारित कर सकते हैं। कुंजियों के अतिरिक्त, आप "Ctrl + कुंजी" पर निर्मित संयोजनों को स्थानांतरित कर सकते हैं जो कुछ संयोजनों को दबाएंगे। उदाहरण के लिए, यदि आप "Ctrl + d" पास करते हैं, तो संयोजन CTRL + ALT + DELETE प्रबंधित कंप्यूटर पर दबाया जाएगा।
ESP8266 पोर्ट को नियंत्रित करने के लिए संयोजन भी हैं, उदाहरण के लिए, आप रिले को कनेक्ट और रिले को चालू और बंद करने के लिए "Ctrl + q" संयोजन का उपयोग कर सकते हैं, जिससे दूरस्थ रूप से चालू कंप्यूटर को चालू करें और बंद करें। आप इन और अन्य संयोजनों को स्रोत में देख सकते हैं।
यदि यह विफल रहा : ESP8266 "TD", पासवर्ड "टेस्टेस्ट" नाम के साथ एक्सेस प्वाइंट मोड पर स्विच करता है और 192.168.4.1 पर पहुंचता है, जहां आप WI-FI के माध्यम से कनेक्ट करने के लिए सेटिंग्स को कॉन्फ़िगर कर सकते हैं, एक छोटा वेब इंटरफ़ेस खोलते हैं।

इस प्रकार, डिवाइस को आसानी से दूसरे एक्सेस प्वाइंट से जोड़ा जा सकता है। हां, मरहम में एक मक्खी यहां छिपी हुई है, हमारे आईपी केवीएम के संचालन के लिए आपको लैन केबल और वाई-फाई दोनों की आवश्यकता होगी। डिवाइस की सस्ताता के लिए इस तरह की लागत होगी।
हमने ESP8266 के साथ निपटा, Atmega16u2 के साथ सब कुछ पिछले लेखों की तरह है, हम फ्लिप कार्यक्रम को फ्लैश करते हैं, फर्मवेयर गीथब से डाउनलोड किए गए संग्रह में है।
घटक कनेक्शन
घटकों के सही कनेक्शन के लिए, मैं सर्किट संलग्न करता हूं। बस ध्यान रखें, यह एक सशर्त योजना है, यह स्पष्टता के लिए कार्य करता है और आदर्श होने का दावा नहीं करता है। हर कोई उसे पसंद करने के लिए "प्रस्तुत" करने के लिए स्वतंत्र है।

मुझे कुछ बिंदुओं की व्याख्या करने दें: आरेख में ट्रांजिस्टर को ESP8266 लोड करने के बाद Atmega16u2 को चालू करने की आवश्यकता होती है, क्योंकि जब आप ESP8266 को चालू करते हैं, तो डिबग जानकारी सभी TX पोर्टों में संचारित होती है, और अगर Atmega16u2 चालू होता है और कंप्यूटर से जुड़ा होता है, तो एक डेटा स्ट्रीम जिसके वॉल्यूम के साथ एक डेटा स्ट्रीम होता है। ड्राइवर सामना नहीं कर सकता। यह निश्चित रूप से ज्ञात नहीं है कि इस समय क्या हो रहा है, ड्राइवर बफर माना जाता है कि अतिप्रवाह हो रहा है, प्रभाव बेहद अप्रिय है: सैकड़ों कुंजी दबाए जाते हैं, यदि एक पाठ संपादक खोला जाता है, तो यह अस्पष्टता का एक गुच्छा डालता है, और सभी सेवा कुंजी अटक जाती हैं और परिणामस्वरूप, कीबोर्ड के साथ काम करना असंभव हो जाता है। । इससे बचने के लिए, Atmega16u2 को ESP8266 लोड करने के बाद संचालित करने की आवश्यकता है। फर्मवेयर में इस क्षण को ध्यान में रखा जाता है।
बेशक, योजना का एक विकल्प है, लेकिन यह अमीर या आलसी के लिए एक विकल्प है। और वैसे, यह विकल्प उपरोक्त को रद्द नहीं करता है:

तस्वीर में, Atmega328p चिप के बिना Arduino UNO NodeMCU के चीनी समकक्ष से जुड़ा है। 3.3 वोल्ट लाइन Arduino पर समान वोल्टेज स्तर की रेखा से जुड़ी है, साथ ही जमीन और GPIO2 पिन (ESP8266) Arduino पर TX पिन से जुड़े हैं।
अंतिम जाँच
हम टेलनेट द्वारा पोर्ट 23 से कनेक्ट करते हैं और प्रदर्शन की जांच करते हैं। आप ऐसा कर सकते हैं:
telnet [ip- ESP8266]
कमांड
telnet [ip- ESP8266]
साथ विंडोज पर।
लिनक्स पर यह थोड़ा और अधिक जटिल होगा:
telnet [ip- ESP8266]
कमांड
telnet [ip- ESP8266]
फिर आपको नियंत्रण चरित्र को दबाने की आवश्यकता है, डिफ़ॉल्ट "Ctrl +]" है, टेलनेट को कमांड मोड में जाना चाहिए, फिर "एल" और "एंटर" दबाएं। इन क्रियाओं के साथ, हम टेलनेट को प्रतीक मोड में बदल देंगे।
$ telnet 192.168.***.*** Trying 192.168.***.***... Connected to 192.168.***.***. Escape character is '^]'. ^] telnet> l
सब कुछ तैयार है, हम हमारे द्वारा बनाए गए डिवाइस के संचालन की जांच कर सकते हैं। मुझे आपको "Alt + Tab", "Ctrl + Alt + Del" और आदि दबाने के लिए संभावित संयोजन याद दिलाना चाहिए। स्केच में देख सकते हैं। बस इतना ही, तीसरा KVM DIY IP अवतार तैयार है।
संक्षेप में देना
पेशेवरों:
- संभवतः सबसे महत्वपूर्ण प्लस मूल्य है, यह 2000 रूबल में फिट होने के लिए निकला
- वीडियो की गुणवत्ता के बारे में कोई शिकायत नहीं होनी चाहिए, आप बिना किसी समस्या के पूर्ण HD तक स्ट्रीम कर सकते हैं
- चार रिले या अन्य एक्ट्यूएटर्स को जोड़कर कार्यक्षमता का विस्तार करने की क्षमता।
विपक्ष:
- वाई-फाई और लैन केबल के माध्यम से कनेक्ट करने की आवश्यकता है
- जब वीजीए के साथ उपयोग किया जाता है, तो एक एडेप्टर की आवश्यकता होती है, जो स्वाभाविक रूप से लागत को प्रभावित करेगा
सामान्य तौर पर, डिवाइस ध्यान से योग्य हो गया है, ज़ाहिर है, यह आईपी केवीएम को अपने सभी "माल" के साथ एक प्रतियोगी नहीं है, लेकिन यह कीमत में बहुत अधिक जीतता है। और घरेलू उपयोग के लिए, और शायद न केवल, यह काफी उपयुक्त है।मैं उपयोगकर्ता DaylightIsBurning को धन्यवाद देने के लिए इस अवसर को लेना चाहूंगा ! इस तरह के आदमी ने खुदाई करने के लिए सही दिशा का सुझाव दिया।आपका ध्यान के लिए धन्यवाद। जल्द मिलते हैं!