I am trying to send over 20 bytes in ionic ble native without success,
first of all I send without response and then this response but still not working
how I do this?
var newSend=this.myInput.match(/.{1,19}/g);
console.log(newSend);
for(var i = 0 ; i<newSend.length ; i++){
var ddd = newSend[i].buffer;
this.sendingtext=newSend[i];
console.log(i,newSend.length);
if(i == (newSend.length-1)){
this.ble.write(bID, bService, bCharacteristic, ddd).then(
function(data){
// console.log( this.myInput);
console.log("write",data);
}
);
}else{
this.ble.writeWithoutResponse(bID, bService, bCharacteristic, ddd).then(
function(data){
// console.log( this.myInput);
console.log("writeWithoutResponse",data);
}
);
}
That is not acceptable. BLE is low energy bluetooth, so it's protocol limit the packet size of a command. In general the maximum payload size you can send over BLE write is 20 bytes
Follow this link to read more about how to send larger 20 bytes over BLE
Android: Sending data >20 bytes by BLE
It's a misconception that Write Without Response doesn't give a response; it does.
You just don't have to wait for response.
It is meant to decrease the time between successive packets,
we can send and receive data between a client and server without waiting for a response after each message.
There are some restrictions:
You have to comply with the MTU of the server.
The receive buffer of the server must be large enough to hold the incoming packets.
There must be enough time for the server to empty the receive buffer.
Related
What will happen if I will establish a connection between a client and a server, and configure a different buffer size for each of them.
This is my client's code:
import socket,sys
TCP_IP = sys.argv[1]
TCP_PORT = int(sys.argv[2])
BUFFER_SIZE = 1024
MESSAGE = "World! Hello, World!"
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((TCP_IP, TCP_PORT))
s.send(MESSAGE)
data = s.recv(BUFFER_SIZE)
s.close()
print "received data:", data
Server's code:
import socket,sys
TCP_IP = '0.0.0.0'
TCP_PORT = int(sys.argv[1])
BUFFER_SIZE = 5
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.bind((TCP_IP, TCP_PORT))
s.listen(1)
while True:
conn, addr = s.accept()
print 'New connection from:', addr
while True:
data = conn.recv(BUFFER_SIZE)
if not data: break
print "received:", data
conn.send(data.upper())
conn.close()
That means I will be limited to only 5 bytes? Which means I won't be able to receive the full packet and will lose 1024-5 packets?
I or does it mean I am able to get only packets of 5 bytes, which means that instead of receiving one packets of 1024 bytes as the client sent it, I'll have to divide 1024 by 5 and get 204.8 packets (?) which sounds not possible.
What in general is happing in that code?
Thanks.
Your arguments are based on the assumption that a single send should match a single recv. But this is not the case. TCP is a byte stream and not a message based protocol. This means all what matters are the transferred bytes. And for this is does not matter if it does not matter if one or 10 recv are needed to read 50 bytes.
Apart from that send is not guaranteed to send the full buffer either. It might only send parts of the buffer, i.e. the sender need actually check the return code to find out how much of the given buffer was actually send now and how much need to be retried for sending later.
And note that the underlying "packet" is again a different thing. If there is a send for 2000 bytes it will usually need multiple packets to be send (depending on the maximum transfer unit of the underlying data link layer). But this does not mean that one also need multiple recv. If all the 2000 bytes are already transferred to the OS level receive buffer at the recipient then they can be also be read at once, even if they traveled in multiple packets.
Your socket won't lose the remaining 1024 - 5 (1019) bytes.it just stored on the socket and ready to read again! so , all you need to do is to read from the socket again. the size of buffer you want to read to is decided by yourself. and you are not limited to 5 bytes, you are just limiting the read buffer for each single read to 5 bytes. so for 1024 bytes to read you have to read for 204 times plus another time read which would be the last one. but remember that the last time read fills your last buffer index with null. and that means there is no more bytes available for now.
The recv() library function man page mention that:
It returns the number of bytes received. It normally returns any data available, up to the requested amount, rather than waiting for receipt of the full amount requested.
If we are using blocking recv() call and requested for 100 bytes:
recv(sockDesc, buffer, size, 0); /* Where size is 100. */
and only 50 bytes are send by the server then this recv() is blocked until 100 bytes are available or it will return receiving 50 bytes.
The scenario could be that:
server crashes after sendign only 50 bytes
bad protocol design where server is only sending 50 bytes while client is expecting 100 and server is also waiting for client's reply (i.e. socket close connection has not been initiated by server in which recv will return)
I am interested on Linux / Solaris platform. I don't have the development environment to check it out myself.
recv will return when there is data in the internal buffers to return. It will not wait until there is 100 bytes if you request 100 bytes.
If you're sending 100 byte "messages", remember that TCP does not provide messages, it is just a stream. If you're dealing with application messages, you need to handle that at the application layer as TCP will not do it.
There are many, many conditions where a send() call of 100 bytes might not be read fully on the other end with only one recv call when calling recv(..., 100); here's just a few examples:
The sending TCP stack decided to bundle together 15 write calls, and the MTU happened to be 1460, which - depending on timing of the arrived data might cause the clients first 14 calls to fetch 100 bytes and the 15. call to fetch 60 bytes - the last 40 bytes will come the next time you call recv() . (But if you call recv with a buffer of 100 , you might get the last 40 bytes of the prior application "message" and the first 60 bytes of the next message)
The sender buffers are full, maybe the reader is slow, or the network is congested. At some point, data might get through and while emptying the buffers the last chunk of data wasn't a multiple of 100.
The receiver buffers are full, while your app recv() that data, the last chunk it pulls up is just partial since the whole 100 bytes of that message didn't fit the buffers.
Many of these scenarios are rather hard to test, especially on a lan where you might not have a lot of congestion or packet loss - things might differ as you ramp up and down the speed at which messages are sent/produced.
Anyway. If you want to read 100 bytes from a socket, use something like
int
readn(int f, void *av, int n)
{
char *a;
int m, t;
a = av;
t = 0;
while(t < n){
m = read(f, a+t, n-t);
if(m <= 0){
if(t == 0)
return m;
break;
}
t += m;
}
return t;
}
...
if(readn(mysocket,buffer,BUFFER_SZ) != BUFFER_SZ) {
//something really bad is going on.
}
The behavior is determined by two things. The recv low water mark and whether or not you pass the MSG_WAITALL flag. If you pass this flag the call will block until the requested number of bytes are received, even if the server crashes. Other wise it returns as soon as at least SO_RCVLOWAT bytes are available in the socket's receive buffer.
SO_RCVLOWAT
Sets the minimum number of bytes to
process for socket input operations.
The default value for SO_RCVLOWAT is
1. If SO_RCVLOWAT is set to a larger value, blocking receive calls normally
wait until they have received the
smaller of the low water mark value or
the requested amount. (They may return
less than the low water mark if an
error occurs, a signal is caught, or
the type of data next in the receive
queue is different than that returned,
e.g. out of band data). This option
takes an int value. Note that not all
implementations allow this option to
be set.
If you read the quote precisely, the most common scenario is:
the socket is receiving data. That 100 bytes will take some time.
the recv() call is made.
If there are more than 0 bytes in the buffer, recv() returns what is available and does not wait.
While there are 0 bytes available it blocks and the granularity of the threading system determines how long that is.
So i got this issue here, I'm using a openfl.net.Socket to connect with my server and receive messages from it.
The problem is the server is sending two messages almost at the same time and my socket appears to read only one, i tried putting a breakpoint on the second message and releasing it just after it stops (like a sleep of 0.5 seconds), and so my client receive both messages, but sending both at almost same time i get only one... Tips?
socket.addEventListener(ProgressEvent.SOCKET_DATA, onResponse);
function onResponse(e:ProgressEvent):Void
{
trace("response");
if (socket.bytesAvailable > 0)
{
var size:Int = socket.readInt();
var domainId:Int = socket.readInt();
var messageId:Int = socket.readInt();
var count:Int = socket.readInt();
var socketData:String = socket.readUTFBytes(socket.bytesAvailable);
trace("RECEIVE: " + socketData);
var message:Message = Message.JSONToMessage(socketData);
Domain.processMessage(message);
}
}
I hope i made myself clear
So, on the receiving side, in one recv you are getting all data that sent from the other end.
One thing you should know about TCP is that it does not maintain message boundaries. It in fact does not know what a "message" is. Its a byte stream protocol. Three sends here will can result in three recv at the other end or even one recv at the other end for the full exchange of data.
Applications using TCP should construct "messages" out of what the TCP is handing over to them. TCP just ensures the data is given in the order it was sent, and tries its best to deliver the packets sent to the receiver. It is up to the application protocol to define what should be done with the data.
I have a problem. When I want to achieve WebSocket server, the server can't send data to the client (in Chrome 16). For example, sending the text "Hello", the server sends the data framing "0x81 0x05 0x48 0x65 0x6c 0x6c 0x6f" to the client, but the browser can't receive the data. Is this code wrong?
sub getSendDataNoMask{
my $dataStr="Hello";
my #ret;
push(#ret,pack("H*","81"));
push(#ret,pack("H*","05"));
push(#ret,$dataStr);
return join("",#ret);
}
What error do you get from the Chrome Javascript console?
You also didn't post your handshake code (the more likely thing to have a problem). Are you certain that the handshake was completed successfully? In other words, did you get an onopen event in the browser?
var ws = WebSocket("ws://myhost:6080/websocket");
ws.onopen = function (e) {
console.log("connection opened");
};
ws.onmessage
console.log("Got data: " + e.data);
};
If you didn't get an opopen event then the handshake never finished successfully. If you are getting on onopen event, then I would try sending data the opposite direction and make sure you can receive and decode frames from your perl server before trying to send.
I starts learning TCP protocol from internet and having some experiments. After I read an article from http://www.diffen.com/difference/TCP_vs_UDP
"TCP is more reliable since it manages message acknowledgment and retransmissions in case of lost parts. Thus there is absolutely no missing data."
Then I do my experiment, I write a block of code with TCP socket:
while( ! EOF (file))
{
data = read_from(file, 5KB); //read 5KB from file
write(data, socket); //write data to socket to send
}
I think it's good because "TCP is reliable" and it "retransmissions lost parts"... But it's not good at all. A small file is OK but when it comes to about 2MB, sometimes it's OK but not always...
Now, I try another one:
while( ! EOF (file))
{
wait_for_ACK();//or sleep 5 seconds
data = read_from(file, 5KB); //read 5KB from file
write(data, socket); //write data to socket to send
}
It's good now...
All I can think of is that the 1st one fails because of:
1. buffer overflow on sender because the sending rate is slower than the writing rate of the program (the sending rate is controlled by TCP)
2. Maybe the sending rate is greater than writing rate but some packets are lost (after some retransmission, still fails and then TCP gives up...)
Any ideas?
Thanks.
TCP will ensure that you don't lose data but you should check how many bytes actually got accepted for transmission... the typical loop is
while (size > 0)
{
int sz = send(socket, bufptr, size, 0);
if (sz == -1) ... whoops, error ...
size -= sz; bufptr += sz;
}
when the send call accepts some data from your program then it's a job of the OS to get that to destination (including retransmission), but the buffer for sending may be smaller than the size you need to send, and that's why the resulting sz (number of bytes accepted for transmission) may be less than size.
It's also important to consider that sending is asynchronous, i.e. after the send function returns the data is not already at the destination, it's has been only assigned to the TCP transport system to be delivered. If you want to know when it will be received then you'll have to use other systems (e.g. a reply message from your counterpart).
You have to check write(socket) to make sure it writes what you ask.
Loop until you've sent everything or you've calculated a time out.
Do not use indefinite timeouts on socket read/write. You're asking for trouble if you do, especially on Windows.