I'm creating windows application in C++, which connect's PC with mobile via bluetooth and winsock. Allow's you to call and send messages from mobile via computer.
I'm using AT command's to tell mobile what i want to do. Pair with mobile device and force a call with At command
ATD+420******;
works perfect, but all commands for handling SMS like
AT+CMGL, AT+CMGF, AT+CMGS etc.
phone probably doesnt recognize them and returns ERROR.
Here is code which connects PC with mobile via bluetooth and socket:
SOCKADDR_BTH RemoteEndPoint;
RemoteEndPoint.port = 0;
RemoteEndPoint.addressFamily = AF_BTH;
RemoteEndPoint.btAddr = m_foundDevices[m_deviceIndex].Address.ullLong;
RemoteEndPoint.serviceClassId = HandsfreeServiceClass_UUID;
int BTHAddrLength = sizeof(RemoteEndPoint);
// Create the socket.
if ((m_localSocket = socket(AF_BTH, SOCK_STREAM, BTHPROTO_RFCOMM)) == INVALID_SOCKET)
{
// handle error.
}
// Connect the socket.
if ((iResult = connect(m_localSocket, (SOCKADDR *)&RemoteEndPoint, sizeof(RemoteEndPoint))) == INVALID_SOCKET)
{
// handle error.
}
Notice line
RemoteEndPoint.serviceClassId = HandsfreeServiceClass_UUID
I think the problem is here, becouse u cant send sms from Handsfree, but when i use another UUID, it doesnt even pair with mobile.
=== Here is just for info, how am i sending and receiving data from mobile ===
char recvbuf[DEFAULT_BUFLEN] = "";
const char *sendbuf = "AT+CMGL\r";
int len = (int)strlen(sendbuf);
if ((iResult = send(m_localSocket, sendbuf, len, MSG_OOB)) == SOCKET_ERROR)
{
// handle error. return ~0
}
if ((iResult = recv(m_localSocket, recvbuf, recvbuflen, 0)) == SOCKET_ERROR)
{
// handle error. return ~0
}
// Here recvbuf == "\r\nERROR\r\n"
-- I would like to find out the problem, why AT command's for SMS doesnt work.
Thank you for any advices!
If you have any question's about problem, i'll kindly explain.
Regards,
Filip.
EDIT
I found out answer "If you want to send SMS Messages, a Server Socket will be needed on the GSM Device", but after hours of googling i have no clue how to do that. Any suggestion's? Thank you.
Related
I'm android developer and facing some autoConnect issue.
I'm using Arduino nano IOT and developed some simple application to communicate.
but I don't know why autoConnect doesn't work in this case.
Arduino nano continuously sends gyroscope sensing data(but only when app connected to module)
below is sample code.
#include <ArduinoBLE.h>
#include <Arduino_LSM6DS3.h>
BLEService sensorService("66df5109-edde-4f8a-a5e1-02e02a69cbd5");
BLEStringCharacteristic xSensorLevel("741c12b9-e13c-4992-8a5e-fce46dec0bff", BLERead | BLENotify,15);
BLEStringCharacteristic ySensorLevel("baad41b2-f12e-4322-9ba6-22cd9ce09832", BLERead | BLENotify,15);
BLEStringCharacteristic zSensorLevel("5748a25d-1834-4c68-a49b-81bf3aeb2e50", BLERead | BLENotify,15);
// last sensor data
float oldXLevel = 0;
float oldYLevel = 0;
float oldZLevel = 0;
long previousMillis = 0;
void setup() {
Serial.begin(9600);
while (!Serial);
if (!IMU.begin()) {
Serial.println("Failed to initialize IMU!");
while (1);
}
pinMode(LED_BUILTIN, OUTPUT);
if (!BLE.begin()) {
Serial.println("starting BLE failed!");
while (1);
}
BLE.setLocalName("Demo Gyroscope");
BLE.setAdvertisedService(sensorService);
sensorService.addCharacteristic(xSensorLevel);
sensorService.addCharacteristic(ySensorLevel);
sensorService.addCharacteristic(zSensorLevel);
BLE.addService(sensorService);
BLE.advertise();
Serial.println("Bluetooth device active, waiting for connections...");
}
void loop() {
BLEDevice central = BLE.central();
if (central) {
Serial.print("Connected to central: ");
Serial.println(central.address());
digitalWrite(LED_BUILTIN, HIGH);
while (central.connected()) {
//long currentMillis = millis();
updateGyroscopeLevel();
delay(300);
}
digitalWrite(LED_BUILTIN, LOW);
Serial.print("Disconnected from central: ");
Serial.println(central.address());
}
}
void updateGyroscopeLevel() {
float x, y, z;
if (IMU.gyroscopeAvailable()) {
IMU.readGyroscope(x, y, z);
if (x != oldXLevel) {
xSensorLevel.writeValue(String(x));
oldXLevel = x;
}
if (y != oldYLevel) {
ySensorLevel.writeValue(String(y));
oldYLevel = y;
}
if (z != oldZLevel) {
zSensorLevel.writeValue(String(z));
oldZLevel = z;
}
Serial.print(x);
Serial.print('\t');
Serial.print(y);
Serial.print('\t');
Serial.println(z);
}
}
and in my android app, I have set autoConnect true
private fun connectDevice(device: BluetoothDevice?) {
// update the status
broadcastUpdate(Actions.STATUS_MSG, "Connecting to ${device?.address}")
bleGatt = device?.connectGatt(context, true, gattClientCallback)
}
App can connect to module and read/write some data using UUID but when I turn off the module and turn on again, App cannot automatically connect it.
As far as I know, once I set it true, android store bt info as cache and trying to reconnect repeatedly.
(fyi, I'm not using Service to maintain connection)
but in my case, when I turn the module on again, it just shows below message in serial monitor
Bluetooth device active, waiting for connections...
It seems like app doesn't retry to connect.
I have read related questions and answers over here but couldn't find clue for my case.
My question over here is am I doing wrong? or this is normal behaviour?
when it comes to bt earphone, it's automatically connected when turn on. so I'm thinking something like that.
Please share any idea for this.
Really appreciate it!
After reading more articles, I found what's the issue.
Not sure if anyone reaching out to this question but in my case, I want app to reconnect to ble automatically even after turning off and on the ble.
But I found turning off/on the phone, turning off/on ble clear the cache in android internally. so Cannot automatically reconnect in this scenario.
Please have a look. this is really helpful for me
https://medium.com/#martijn.van.welie/making-android-ble-work-part-2-47a3cdaade07
This is not an answer but I found autoConnect is working when I use nRF Connect application. that means BT module itself has no issue and my application has issue.
I am attempting to using an IOIO-RTG board to control a MCP-4131 digital potentiometer via SPI. I'm new to SPI but I believe that I've followed the SPI example. I'm able to set a resistance apparently but IOIO remains stuck afterwards. The only way to continue is to disconnect and reconnect to the board. I note that the SPI example expects a MISO and MOSI pin whereas the pot has a combined SDI/SDO pin. Is this difference the source of my issue?
IOIO RTG
IOIOLIb 0326
Application Firmware 0506
Bootloader Firmware 0402
Hardware Sprk 0020
I've tried to implement asynchronous transactions to not wait for a response but the end result is the same. I've called the highgear function from within the Looper class and outside with no change.
class Looper extends BaseIOIOLooper
{
SpiMaster spi;
protected void setup() throws ConnectionLostException
{
int clkPin = 39;//left side = 36
int misoPin = 38;//left side = 33, not expecting output
int mosiPin = 38;//left side = 35
spi = ioio_.openSpiMaster(new DigitalInput.Spec(misoPin,
Mode.PULL_UP), new DigitalOutput.Spec(mosiPin),
new DigitalOutput.Spec(clkPin),
new DigitalOutput.Spec[] { new DigitalOutput.Spec(40), new DigitalOutput.Spec(37), },
new SpiMaster.Config(Rate.RATE_125k, true, true));
}
public void highgear()
{
byte[] request = new byte[] {0,0,0,0,0,5,5,5};
byte[] response = new byte[4];
try {
SpiMaster.Result result = spi.writeReadAsync(0, request, request.length, 7, response, 0);
} catch (ConnectionLostException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
The expected outcome is that the MCP with give the desired resistance and the IOIO will be available for further commanding. There are no errors as the board just freezes in it's set configuration.
The shared SDO/SDI pin of the MCP-4131 should not be the problem.
From the datasheet on page 31: "The 8-lead Single Potentiometer devices are pin limited so the SDO pin is multiplexed with the SDI pin (SDI/SDO pin). After the Address/Command (first 6-bits) are received, If a valid Read command has been requested, the SDO pin starts driving the requested read data onto the SDI/SDO pin."
As long as you only write to the digital potentiometer everything should be the same as with other SPI devices.
Have you tried your code with other SPI devices or even without connecting one?
i'm working for a project using arduino and android studio, I would like to control my arduino from my mobile application by sending 0 t of 1, then I would like to receive arduino data on my android application,it is an obstacle detector that sends warning when there is an obstacle, here is the code of the arduino, it works because I tested with an application that I downloaded from google play, now I do not know how to display the message sent by arduino on my mobile application, and also how control the arduino from my app.
int echo = 3;
int trig = 2;
int greenled=4;
int redled=5;
float timelapse;
float distance;
char state=' ';
void setup() {
pinMode(greenled, OUTPUT);
pinMode(redled, OUTPUT);
pinMode(trig,OUTPUT);
pinMode(echo,INPUT);
digitalWrite(trig,LOW);
digitalWrite(greenled,LOW);
digitalWrite(redled,LOW);
Serial.begin(9600);
}
void loop() {
if (Serial.available()>0){
digitalWrite(trig,HIGH);
delayMicroseconds(10);
digitalWrite(trig,LOW);
timelapse=pulseIn(echo,HIGH);
distance = timelapse/58 ;
// if (distance > 200 || distance< 0 ) { Serial.println ( "Out of range"); }
if ( distance < 100 ) {
digitalWrite(redled, HIGH);
digitalWrite(greenled,LOW);
Serial.println("Attention");
delay(150);
}
else {
digitalWrite(redled,LOW);
digitalWrite(greenled,HIGH);
Serial.println("Libre");
}
delay(50);
}
else {
digitalWrite(redled,LOW);
digitalWrite(greenled,LOW);
digitalWrite(trig,LOW);
}
}
You didn't specify anything about how you're connecting your Arduino with your mobile phone. There are multiple ways to connect them together.
My wild guess here is that you're using a wired connection, as I see no code related to Bluetooth or any other communication.
If you're using OTG wired connection then, this would help.
Incase you want to do it wirelessly, you can read and write using serial port to a PC/Pi and then use a python script to upload the data to a cloud like firebase, and then read and data in your Android app from firebase. This is just one suggestion, there are many.
I'm working on an android app where I need to communicate with a bluetooth LE device and in the middle of the communication I receive a callback:
onCharacteristicWrite()
...which is expected. But the status of the operation is 134 instead of 0 (=success).
This GATT status constant is not defined in the official API but here is a translation in one of many unofficial lists:
public static final int GATT_CMD_STARTED = 134;
See: https://code.google.com/r/naranjomanuel-opensource-broadcom-ble/source/browse/framework/java/src/com/broadcom/bt/service/gatt/GattConstants.java?r=983950f9b35407446bf082633d70c7655c206d22
The consequence, that I can see, in my app is that I do not get an expected callback to:
onCharacteristicChanged()
Does anybody know what GATT_CMD_STARTED means? Is it an error?
The description of the following function taken from the bludroid sources hint that something is not working correctly in your GATT server.
Commands seem to "queue up" there, as there must be pending requests or value confirmations as hinted in the comment before the if(...) clause.
It might be worth checking what exactly is going on before you do the writeCharacteristic(...) as it seems to not finish correctly or create hiccups in your server.
/*******************************************************************************
**
** Function attp_cl_send_cmd
**
** Description Send a ATT command or enqueue it.
**
** Returns GATT_SUCCESS if command sent
** GATT_CONGESTED if command sent but channel congested
** GATT_CMD_STARTED if command queue up in GATT
** GATT_ERROR if command sending failure
**
*******************************************************************************/
tGATT_STATUS attp_cl_send_cmd(tGATT_TCB *p_tcb, UINT16 clcb_idx, UINT8 cmd_code, BT_HDR *p_cmd)
{
tGATT_STATUS att_ret = GATT_SUCCESS;
if (p_tcb != NULL)
{
cmd_code &= ~GATT_AUTH_SIGN_MASK;
/* no pending request or value confirmation */
if (p_tcb->pending_cl_req == p_tcb->next_slot_inq ||
cmd_code == GATT_HANDLE_VALUE_CONF)
{
att_ret = attp_send_msg_to_l2cap(p_tcb, p_cmd);
if (att_ret == GATT_CONGESTED || att_ret == GATT_SUCCESS)
{
/* do not enq cmd if handle value confirmation or set request */
if (cmd_code != GATT_HANDLE_VALUE_CONF && cmd_code != GATT_CMD_WRITE)
{
gatt_start_rsp_timer (clcb_idx);
gatt_cmd_enq(p_tcb, clcb_idx, FALSE, cmd_code, NULL);
}
}
else
att_ret = GATT_INTERNAL_ERROR;
}
else
{
att_ret = GATT_CMD_STARTED;
gatt_cmd_enq(p_tcb, clcb_idx, TRUE, cmd_code, p_cmd);
}
}
else
att_ret = GATT_ERROR;
return att_ret;
}
Starts at line 469 in android sources.
The native GATT error and statuscodes can be found here.
I am beginning the basis for a home automation system using an arduino with ethernet and a phone with software that I programmed with MIT App inventor. I've been playing with code from a tutorial and got my LED to turn on and off fine from a local computer using the internet by using a browser and navigating the url 192.168.1.10/$1
/* thrown together by Randy Sarafan
Allows you to turn on and off an LED by entering different urls.
To turn it on:
http://192.168.1.10/$1
To turn it off:
http://192.168.1.10/$2
Based almost entirely upon Web Server by Tom Igoe and David Mellis
Edit history:
created 18 Dec 2009
by David A. Mellis
modified 4 Sep 2010
by Tom Igoe
*/
#include <SPI.h>
#include <Ethernet.h>
boolean incoming = 0;
// Enter a MAC address and IP address for your controller below.
// The IP address will be dependent on your local network:
byte mac[] = { 0x00, 0xAA, 0xBB, 0xCC, 0xDA, 0x02 };
//IPAddress ip(191,168,1,15); //<<< ENTER YOUR IP ADDRESS HERE!!! i commented this out and did it on the router side
// Initialize the Ethernet server library
// with the IP address and port you want to use
// (port 80 is default for HTTP):
EthernetServer server(80);
void setup()
{
pinMode(8, OUTPUT);
// start the Ethernet connection and the server:
Ethernet.begin(mac);
server.begin();
Serial.begin(9600);
}
void loop()
{
// listen for incoming clients
EthernetClient client = server.available();
if (client) {
// an http request ends with a blank line
boolean currentLineIsBlank = true;
while (client.connected()) {
if (client.available()) {
char c = client.read();
// if you've gotten to the end of the line (received a newline
// character) and the line is blank, the http request has ended,
// so you can send a reply
//reads URL string from $ to first blank space
if(incoming && c == ' '){
incoming = 0;
}
if(c == '$'){
incoming = 1;
}
//Checks for the URL string $1 or $2
if(incoming == 1){
Serial.println(c);
if(c == '1'){
Serial.println("ON");
digitalWrite(8, HIGH);
}
if(c == '2'){
Serial.println("OFF");
digitalWrite(8, LOW);
}
}
if (c == '\n') {
// you're starting a new line
currentLineIsBlank = true;
}
else if (c != '\r') {
// you've gotten a character on the current line
currentLineIsBlank = false;
}
}
}
// give the web browser time to receive the data
delay(1);
// close the connection:
client.stop();
}
}
The problem I'm having is on the mobile side. I created an app with MIT app inventor that should toggle the IP, but instead gives me:
error 1109: The specified URL is not valid: 192.168.1.10/$1
Im quite perplexed. I know that this URL IS VALID because I've connected to it before. Is there a way to override this or otherwise fix it?
Here's the MIT app inventor AIA source: http://www.filedropper.com/internetled
You SHOULD specify the IP address in the code itself. And change "Ethernet.begin(mac);" to "Ethernet.begin(mac, ip);".
You should also try to open the web page in the browser to check if it works, before trying it out with App Inventor.
In AppInventor error "error 1109: The specified URL is not valid: 192.168.1.10/$1" you may have forgotten to put the "http: //" in your address.
Example, if you are saving the address in a global variable or tinyDB, you should put http://192.168.1.10/$1
This would be your address to connect the led.