दिलचस्प पोस्ट
PHP सरणी संयोजन किसी एप्लिकेशन के लिए कई इंटरनेट कनेक्शनों में से एक चुनें मैं निष्पादित करने वाले पर्ल स्क्रिप्ट का पूरा रास्ता कैसे प्राप्त करूं? एकाधिक जीआईटी वापस आना Vb6 में प्रोग्रामिंग में थ्रेड का उपयोग करने के लिए किसी स्विंग विंडो के सापेक्ष किसी माउस क्लिक का स्थान कैसे प्राप्त करें UIWebView – "अंतिम" वेबव्यूडिफ़फ़िन्शिप संदेश को कैसे पहचानें? जब एक HTML5 वीडियो समाप्त हो जाए, तब पता लगाएं एक दूरस्थ फ़ाइल की अंतिम संशोधित दिनांक प्राप्त करें बिट मास्किंग क्या है? एक्लिप्स डीबगर में चरण इन्टो और स्टेप ओवर के बीच अंतर क्या है? सहिष्णुता के साथ तार की तुलना करना रीसपर सभी के लिए 'var' का उपयोग क्यों करना चाहता है? SQL में समय-अंतराल ओवरलैप के साथ पंक्तियों को खोजने का एक सरल और कारगर तरीका क्या है? एक्सेल (.XLS और .XLSX) सी # से फ़ाइल बनाएँ

एक ही पोर्ट पर कई मल्टीकास्ट फ़ीड प्राप्त करना – सी, लिनक्स

मेरे पास एक ऐसा अनुप्रयोग है जो एक ही पोर्ट पर एकाधिक मल्टीकास्ट स्रोतों से डेटा प्राप्त कर रहा है। मुझे डेटा मिल पा रहा है। हालांकि, मैं प्रत्येक समूह के आँकड़ों के लिए खाते की कोशिश कर रहा हूं (यानी प्राप्त संदेश, प्राप्त बाइट्स) और सभी डेटा मिश्रित हो रहे हैं। क्या किसी को यह समस्या हल करने के लिए पता है? अगर मैं प्रेषक के पते को देखने की कोशिश करता हूं, यह मल्टिकास्ट पता नहीं है, बल्कि भेजने मशीन के आईपी है।

मैं निम्नलिखित सॉकेट विकल्पों का उपयोग कर रहा हूं:

struct ip_mreq mreq; mreq.imr_multiaddr.s_addr = inet_addr("224.1.2.3"); mreq.imr_interface.s_addr = INADDR_ANY; setsockopt(s, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq)); 

और भी:

 setsockopt(s, SOL_SOCKET, SO_REUSEPORT, &reuse, sizeof(reuse)); 

मैं किसी भी मदद की सराहना !!!

Solutions Collecting From Web of "एक ही पोर्ट पर कई मल्टीकास्ट फ़ीड प्राप्त करना – सी, लिनक्स"

[स्पष्ट करने के लिए संपादित करें कि bind() वास्तव में एक मल्टीकास्ट पता शामिल हो सकता है।]

इसलिए यह अनुप्रयोग कई मल्टीकास्ट समूहों में शामिल हो रहा है, और उनमें से किसी को भी एक ही पोर्ट पर भेजे गए संदेश प्राप्त कर रहा है। SO_REUSEPORT आपको एक ही बंदरगाह में कई कुर्सियां ​​बाँध करने की अनुमति देता है। बंदरगाह के अलावा, bind() को एक आईपी पता की जरूरत है INADDR_ANY एक कैच-ऑल एड्रेस है, लेकिन एक मल्टीकास्ट वाला एक आईपी एड्रेस भी इस्तेमाल किया जा सकता है। उस स्थिति में, उस आईपी को भेजे गए पैकेट केवल सॉकेट पर वितरित किए जाएंगे। Ie आप कई कुर्सियां ​​बना सकते हैं, एक प्रत्येक मल्टीकास्ट समूह के लिए। (group_addr, port) के लिए प्रत्येक सॉकेट bind() , और group_addr में शामिल हों तब विभिन्न समूहों को संबोधित डेटा अलग-अलग सॉकेट पर दिखाए जाएंगे, और आप इस तरह से इसे अलग करने में सक्षम होंगे।

मैंने परीक्षण किया है कि फ्रीब्सडी पर निम्नलिखित कार्य करता है:

 #include <sys/socket.h> #include <stdio.h> #include <string.h> #include <arpa/inet.h> #include <netinet/in.h> #include <sys/param.h> #include <unistd.h> #include <errno.h> int main(int argc, const char *argv[]) { const char *group = argv[1]; int s = socket(AF_INET, SOCK_DGRAM, 0); int reuse = 1; if (setsockopt(s, SOL_SOCKET, SO_REUSEPORT, &reuse, sizeof(reuse)) == -1) { fprintf(stderr, "setsockopt: %d\n", errno); return 1; } /* construct a multicast address structure */ struct sockaddr_in mc_addr; memset(&mc_addr, 0, sizeof(mc_addr)); mc_addr.sin_family = AF_INET; mc_addr.sin_addr.s_addr = inet_addr(group); mc_addr.sin_port = htons(19283); if (bind(s, (struct sockaddr*) &mc_addr, sizeof(mc_addr)) == -1) { fprintf(stderr, "bind: %d\n", errno); return 1; } struct ip_mreq mreq; mreq.imr_multiaddr.s_addr = inet_addr(group); mreq.imr_interface.s_addr = INADDR_ANY; setsockopt(s, IPPROTO_IP, IP_ADD_MEMBERSHIP, &mreq, sizeof(mreq)); char buf[1024]; int n = 0; while ((n = read(s, buf, 1024)) > 0) { printf("group %s fd %d len %d: %.*s\n", group, s, n, n, buf); } } 

यदि आप कई मल्टीकास्ट पतों के लिए ऐसी कई प्रक्रियाएं चलाते हैं, और एक पते पर एक संदेश भेजते हैं, तो केवल प्रासंगिक प्रक्रिया उसे प्राप्त होगी बेशक, आपके मामले में, आप शायद एक ही प्रक्रिया में सभी कुर्सियां ​​बनाना चाहते हैं, और आपको उन सभी को पढ़ने के लिए select या poll या समतुल्य का उपयोग करना होगा।

कुछ वर्षों के बाद इस लिनक्स अजीब व्यवहार का सामना करना पड़ता है, और बाइंड समाधान का उपयोग पिछले उत्तरों में किया जाता है , मुझे एहसास है कि आईपी ​​(7) मैनपेज एक संभावित समाधान का वर्णन करता है:

IP_MULTICAST_ALL (लिनक्स 2.6.31 से)
यह विकल्प वाइल्डकार्ड INADDR_ANY पते से जुड़ी सॉकेट पर बहुस्त्र्पीय संदेशों की वितरण नीति को संशोधित करने के लिए उपयोग किया जा सकता है। तर्क एक बुलियन पूर्णांक है (1 के लिए चूक)। यदि 1 पर सेट किया गया है, तो सॉकेट उन सभी समूहों के संदेश प्राप्त करेगा जो संपूर्ण सिस्टम पर विश्व स्तर पर शामिल हो गए हैं। अन्यथा, यह केवल उन समूहों से संदेश वितरित करेगा जो इस विशेष सॉकेट पर स्पष्ट रूप से शामिल हुए हैं (उदाहरण के लिए आईपी_एडीडी_एमएमएआरएचएचएच विकल्प के जरिए)

इसके बाद आप इन समूहों के संदेश प्राप्त करने के लिए फ़िल्टर को सक्रिय कर सकते हैं:

 int mc_all = 0; if ((setsockopt(sock, IPPROTO_IP, IP_MULTICAST_ALL, (void*) &mc_all, sizeof(mc_all))) < 0) { perror("setsockopt() failed"); } 

यह समस्या और इसे IP_MULTICAST_ALL को सक्षम करने का तरीका Redhat बग 231899 में चर्चा की गई है, इस चर्चा में समस्या को पुन: उत्पन्न करने और इसे हल करने के लिए परीक्षण कार्यक्रम शामिल हैं

अपने प्लेटफॉर्म के आधार पर IP_PKTINFO setsockopt() और IP_PKTINFO या IP_RECVDSTADDR उपयोग करें, आईपीवी 4 को संभालने के लिए। यह recvmsg() या WSARecvMsg() के साथ संयुक्त आप प्रत्येक पैकेट के स्रोत और गंतव्य पते को खोजने के लिए अनुमति देता है।

यूनिक्स / लिनक्स, IP6_PKTINFO लिए IP6_PKTINFO समर्थन करता है, जबकि IP_RECVDSTADDR शुल्क IP_RECVDSTADDR का उपयोग करता है।

विंडोज़ में भी IP_ORIGINAL_ARRIVAL_IF

बदलने के

mc_addr.sin_addr.s_addr = htonl(INADDR_ANY);

साथ में

mc_addr.sin_addr.s_addr = inet_addr (mc_addr_str);

यह मेरे लिए (लिनक्स) मदद है, प्रत्येक आवेदन के लिए मैं एक बंदरगाह पर अलग mcast समूह से अलग mcast स्ट्रीम प्राप्त करता हूं।

इसके अलावा आप वीएलसी प्लेयर के स्रोत को देख सकते हैं, यह एक बंदरगाह पर अलग-अलग mcast समूह से कई mcast iptv चैनल दिखाता है, लेकिन मुझे पता नहीं, यह कैसे चैनल separetes।

मुझे प्रत्येक मल्टीकास्ट समूह के अलग-अलग पते देखकर कई सॉकेट्स का उपयोग करना पड़ता है, और तब प्रत्येक सॉकेट पर अलग-अलग आँकड़ों की गणना करना होता है

अगर ऊपर दिए गए उत्तर में उल्लिखित "रिसीवर के पते" को देखने का एक तरीका है, तो मैं इसे समझ नहीं पा रहा हूं।

एक महत्वपूर्ण बिंदु जो मुझे थोड़ी देर भी ले गया – जब मैंने प्रत्येक व्यक्तिगत कुर्सियां ​​एक रिक्त पते पर बाँध दीं जैसे सबसे अजगर उदाहरण हैं:

 sock[i].bind(('', MC_PORT[i]) 

मुझे प्रत्येक सॉकेट पर सभी मल्टीकास्ट पैकेट (सभी मल्टीकास्ट समूहों से) मिला, जो इससे मदद नहीं मिली। इसे ठीक करने के लिए, मैंने प्रत्येक सॉकेट को अपनी मल्टीकास्ट समूह में बांट दिया

 sock[i].bind((MC_GROUP[i], MC_PORT[i])) 

और फिर काम किया

IIRC recvfrom () आपको प्रत्येक प्रेषक के लिए एक अलग पठन पते / पोर्ट देता है।

आप स्रोत प्रेषक की पहचान करने वाले प्रत्येक पैकेट में हेडर भी डाल सकते हैं।

मल्टिकास्ट पता प्राप्तकर्ता का पता पैकेट में प्रेषक का पता नहीं होगा। रिसीवर के आईपी पते को देखो।

आप प्राप्त पैकेट के गंतव्य आईपी पते (जो कि हमेशा मल्टिकास्ट पते होंगे) को देखकर मल्टिकास्ट स्ट्रीम को अलग कर सकते हैं। यह कुछ ऐसा करने के लिए शामिल है:

IP_PKTINFO से IP_PKTINFO और IP_PKTINFO सॉकेट विकल्प सेट करें। फिर आपको अपने मल्टीकास्ट UDP पैकेट प्राप्त करने के लिए और IP_PKTINFO नियंत्रण संदेश को स्कैन करने के लिए recvmsg() का उपयोग करना होगा। यह आपको प्राप्त यूडीपी पैकेट की कुछ पक्ष बैंड जानकारी देता है:

 struct in_pktinfo { unsigned int ipi_ifindex; /* Interface index */ struct in_addr ipi_spec_dst; /* Local address */ struct in_addr ipi_addr; /* Header Destination address */ }; 

Ipi_addr को देखो: यह यूडीपी पैकेट के मल्टीकास्ट पता होगा जो आपने अभी प्राप्त किया है। अब आप प्राप्त प्रत्येक मल्टिकास्ट स्ट्रीम (मल्टिकास्ट पता) के लिए प्राप्त किए गए पैकेट विशिष्ट संभाल सकते हैं।