PlatformIO library inclusion stinks

I don’t know. I admit that. I’m using this forum a lot, and i’m getting a lot of help. But nothing has helped get me past this impossible problem.

Libraries and the ease of including them is one of PlatformIO’s big selling points, but it clearly doesn’t work.

These libraries demanded by PlatformIO are in a thousand folders on this PC, including the /lib folders where they belong. They’re also in my libraries folder, attached to the .ini:
lib_extra_dirs = ${sysenv.HOMEDRIVE}${sysenv.HOMEPATH}\Documents\libraries

lib_deps = Arduino
lib_deps = CurieBLE

The library wizard can’t find any of the libraries I need. CurieBLE, for example.

As a relatively new arrival, I feel like I’ve gotten to a place where something big and important doesn’t work at all.

Ooops. Does that even work? Anyway, that shouldn’t work and shouldn’t be used. Arduino is a framework, not a library. Instead, you should and probably have this line in your platformio.ini:

framework = arduino

I don’t use the .platformio/lib folder – at all. This folder is empty in my computer. I think it’s bad practice to install libraries globally and I hope PlatformIO will change the UI so this option doesn’t exist anymore.

Instead I strongly recommend:

  • Use lib_deps whenever possible and let PlatformIO do the rest
  • Download and unpack into the project’s lib directory if the library needs to be modified
  • Use lib_extra_dirs if you maintain a library in your own repository

And regarding:

CurieBLE is part of the Arduino Intel core. So it’s only available for a single board: Arduino/Genuino 101. If you have that board and want to use it, you don’t need to specify anything particular in platformio.ini. It’s not a library. It’s part of the core. Just use:

#include <CurieBLE.h>
2 Likes

Thanks- this is an excellent response, because i can’t ask questions about the over-my-head stuff. I have to hear about it from people like you.

All the instruction I’ve seen so far tells me to include Arduino.h as a library if I want to use the Arduino framework and take advantage of some of the hand-holding they do. I want to use the ESP-IDF framework, but I can’t yet. I’m behind on some learning goals due to typical migrant problem like language and knowing where things are. But the libraries thing is making me nuts. It’s easy in Arduino.

I like the idea of global libraries, because the stuff I’m doing should only end up using a handful of libraries. I’ve downloaded a lot with the future in mind.

I’ll include the code that calls for CurieBLE.h. I think i have to break it up. it’s a long script.

So you’re telling me I should only add ‘physical’ library files to the project’s /lib folder?
I appreciate that these files are piles of piles of commands that can’t simplify anything. The code only calls for the contents of one folder.

After I delete all the libraries I’ll never use, I want to be left with a good folder full of all the sensors and modules’ libraries and just link that folder to every script that uses libraries.

Does including global libraries increase the number of variables or objects in the running program?

Should I create an online folder and point to that, or make a GitHub repository?

These two libraries may be freaks, but Arduino.h has to be in half the PlatformIO files in existence. Why can’t I get that to to work??

This is what I’m going to do unless you give me better advice:
I’m going to create a new folder for global libraries, but only add the ones in use. Most of my code will use a handful of them routinely, and some will be edited for I2C address or something. I’ll use extra_dirs with this lean library of libraries.

/*

   Copyright (c) 2016 Intel Corporation.  All rights reserved.

   See the bottom of this file for the license terms.

*/

/*

 * Sketch: BatteryMonitor.ino

 *

 * Description:

 *     This sketch example partially implements the standard Bluetooth

 *   Low-Energy Battery service and connection interval paramater update.

 *

 *   For more information:

 *     https://developer.bluetooth.org/gatt/services/Pages/ServicesHome.aspx

 *

 */

#include <Arduino.h>

#include <CurieBLE.h>

BLEService batteryService("180F"); // BLE Battery Service

// BLE Battery Level Characteristic"

BLEUnsignedCharCharacteristic batteryLevelChar("2A19",  // standard 16-bit characteristic UUID

    BLERead | BLENotify);     // remote clients will be able to

// get notifications if this characteristic changes

int oldBatteryLevel = 0;  // last battery level reading from analog input

long previousMillis = 0;  // last time the battery level was checked, in ms

void setup() {

  Serial.begin(9600);    // initialize serial communication

  pinMode(13, OUTPUT);   // initialize the LED on pin 13 to indicate when a central is connected

  // begin initialization

  BLE.begin();

  /* Set a local name for the BLE device

     This name will appear in advertising packets

     and can be used by remote devices to identify this BLE device

     The name can be changed but maybe be truncated based on space left in advertisement packet

  */

  BLE.setLocalName("BatteryMonitor");

  BLE.setAdvertisedService(batteryService);  // add the service UUID

  batteryService.addCharacteristic(batteryLevelChar); // add the battery level characteristic

  BLE.addService(batteryService);   // Add the BLE Battery service

  batteryLevelChar.setValue(oldBatteryLevel);   // initial value for this characteristic

  /* Start advertising BLE.  It will start continuously transmitting BLE

     advertising packets and will be visible to remote BLE central devices

     until it receives a new connection */

  // start advertising

  BLE.advertise();

  Serial.println("Bluetooth device active, waiting for connections...");

}

void loop() {

  // listen for BLE peripherals to connect:

  BLEDevice central = BLE.central();

  // if a central is connected to peripheral:

  if (central) {

    Serial.print("Connected to central: ");

    // print the central's MAC address:

    Serial.println(central.address());

    // turn on the LED to indicate the connection:

    digitalWrite(13, HIGH);

    // check the battery level every 200ms

    // as long as the central is still connected:

    while (central.connected()) {

      long currentMillis = millis();

      // if 200ms have passed, check the battery level:

      if (currentMillis - previousMillis >= 200) {

        previousMillis = currentMillis;

        updateBatteryLevel();

      }

    }

    // when the central disconnects, turn off the LED:

    digitalWrite(13, LOW);

    Serial.print("Disconnected from central: ");

    Serial.println(central.address());

  }

}

void updateBatteryLevel() {

  /* Read the current voltage level on the A0 analog input pin.

     This is used here to simulate the charge level of a battery.

  */

  int battery = analogRead(A0);

  int batteryLevel = map(battery, 0, 1023, 0, 100);

  if (batteryLevel != oldBatteryLevel) {      // if the battery level has changed

    Serial.print("Battery Level % is now: "); // print it

    Serial.println(batteryLevel);

    batteryLevelChar.setValue(batteryLevel);  // and update the battery level characteristic

    oldBatteryLevel = batteryLevel;           // save the level for next comparison

  }

}

/*

   Copyright (c) 2016 Intel Corporation.  All rights reserved.

   This library is free software; you can redistribute it and/or

   modify it under the terms of the GNU Lesser General Public

   License as published by the Free Software Foundation; either

   version 2.1 of the License, or (at your option) any later version.

   This library is distributed in the hope that it will be useful,

   but WITHOUT ANY WARRANTY; without even the implied warranty of

   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU

   Lesser General Public License for more details.

   You should have received a copy of the GNU Lesser General Public

   License along with this library; if not, write to the Free Software

   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA

*/

If you paste code, please format it as code. I’ve edited your post (without removing all the extra empty lines). Please do it yourself the next time. It’s just polite to invest your time for this and not expect many readers to spend extra time reading your post if you expect them to help you.

Regarding the libraries: Are you sure this is a well spent effort? You’re still learning many things about PlatformIO and ESP32. Would it be easier for now to go with the easier path that creates less problems?

You said that you want to program ESP-IDF. It’s a framework like Arduino and in general Arduino and ESP-IDF cannot be mixed. If you see #include <Arduino.h>, it usually means that it is not compatible with ESP-IDF. Arduino.h will be found if you use the Arduino framework. Could that be one of the problems you’re fighting with?

And regarding the posted sample sketch: it uses CurieBLE, i.e. it does not work on ESP32. So you have to look for another Bluetooth sketch. But first you need to decide which framework you want to use:

  • If you use the Arduino framework, go with this example.
  • If you use the ESP-IDF framework, go with this example.

Note: BLE with ESP-IDF is really hard: it’s complicated and badly documented.

1 Like

Thank you. I never considered format. Sorry.

This is not ESP IDF. I’m not able to do that. I’m okay with ditching this script if it won’t work. I’m getting some HC-05 doodads, so I’ll do it with an Uno or a Nano, in the Arduino framework.

But why won’t the libraries get recognized?

I want to learn a smart way to do libraries and do it that way until something changes, and I feel like I know nothing when I clearly can’t get libraries in the correct directory to work…

Thanks for the heads up about BLE on ESP-IDF. I assumed the makers of bluetooth devices would have a good method published.

What libraries? Please provide a specific example and then we can support you.

Look at the image up top. I’ve got the library files in the /lib folder, and I’ve been attaching my big folder of libraries using the extra_dirs bit in the .ini file.

I can’t get PlatformIO to admit that it has the libraries, and it’s preventing my growth. I’ve got language problems, hardware stuff, lots of PC and Windows stuff to deal with, and meanwhile this thing that looks like it should make sense doesn’t make sense. Clearly somebody knows how to do it. Really want to get there.

In the image, Arduino and CurieBLE are highlighted. Neither one of them is a library as described above.

Please provide a specific example (including platformio.ini, main.cpp and the build log with error messages) and then we can support you. Your are likely doing something wrong but without seeing the files and the output, we have no chance of figuring out what exactly you are doing.

I’m going to accept that this script will never work, and there are reasons why these non-libraries are not being recognized as libraries, which in fact they aren’t?

Maybe it won’t come up again, but I expect to see it again. A library won’t be available in the PIO database, and I won’t be able to get it recognized. Or maybe it will never happen again. But I hate unexplained disappearances of problems almost as much as I need to solve problems.

Thank you for your help.

For starters, neither the Arduino library (folder) or CurieBLE library (folder) should be present in the global .platformio\libs folder.

Maybe this will make it clearer. Not all #includes / libraries are libraries which you (the end user) should be managing, or be having anything to do with. Nor should be putting in any folders manually. Framework provided libraries are just that, libraries provided by the framework (e.g. Arduino), and all you do is do an #include when you want to use them. That’s it. Another example would be the libraries provided by the ESP8266Arduino framework… you don’t install/manage libraries like ESP8266WiFi.h, FS.h, ESP8266mDNS.h, ArduinoOTA.h, Ticker.h, etc… you just include them and they are there.

So, for libraries that are provided by the framework, if they are not found, something is misconfigured in your platformio.ini. Also, since they are provided by the framework (arduino in this case), there is also no need to use lib_deps to instruct platformio that it needs to download them. Finally, there should only be one lib_deps = reference in your platformio.ini. If you need to list multiple libraries, list them one after the other like this

lib_deps =
	RF24
	RF24Network

If you don’t have framework = arduino in your platformio.ini, that’s your problem.

Given that CurieBLE is specific to the Genuino101, I created a new project using your code, and used the following platformio.ini:

[env:genuino101]
platform = intel_arc32
board = genuino101
framework = arduino

It failed to compile …

image

… because the function was used before it was declared. Adding the declaration at the top …

image

… and it compiles just fine. And as you can see from the above screenshot, no IntelliSense / red squiggle issues.

3 Likes

#include <Arduino.h>’ raises errors every time I’ve tried to use it.

This one has frustrated me too much. I have to quit and come back when I can code.

I started with unmodified .ini files, then added some lib_deps, then linked my /libaries folder. The libraries I want to use are all the standard libraries for Adafruit sensors, etc. But I haven’t gotten anything going yet, largely due to the kind of coding problem you found. I’m coming from Arduino, which isn’t really C++. I need to get my hands on a folder of example scripts, to see how to define these modules and get them to initialize.

Thanks for your help. I try to come here for PlatformIO help, not ‘learning about computers’ help.

Or instead of jumping all over the place, you could provide a complete project (i.e. platformio.ini, main source code, and the complete build log) and we’ll try to explain to you what is wrong.

From what I can tell, you keep using using libraries with incompatible frameworks/boards, and wonder why the compiler is telling you there is something wrong. But that is only a guess with the limited information you have given.

1 Like

I have been informed that the library I wanted to load is for an oddball board and I can’t use it. I will assume that’s why i couldn’t get it to unsquiggle.

Today I needed a library that was in the PIO database, and I added it. I had to restart my computer for it to be recognized, but it is recognized on restart. And I added Arduino.h, and nothing bad happened.

Thank you for your help.

Not oddball, just that it’s specific to the one board. But yes, you would be assuming correctly, as if you’re not using the right framework / board, the library won’t be found, because as far as the compiler is concerned, it doesn’t exist, or isn’t valid.

You shouldn’t have needed to restart your computer. At worse case, just your code editor. Regardless, if you add a library, and it isn’t immediately recognised (i.e. has the IntelliSense red squiggle), just build it anyway - it will most likely be downloaded as part of the compile process, and the squiggle will go away, as the library exists on your computer, and IntelliSense has finally worked it out.

I added ‘void updateBatteryLevel();’, and I got this:

Compiling .pio\build\esp32doit-devkit-v1\libda2\CurieBLE\BLEDescriptor.cpp.o
In file included from lib\CurieBLE\src/CurieBLE.h:33:0,
                 from src\main.cpp:18:
lib\CurieBLE\src/BLECommon.h:26:54: fatal error: ../src/services/ble_service/ble_protocol.h: No such file or directory
compilation terminated.
*** [.pio\build\esp32doit-devkit-v1\src\main.cpp.o] Error 1
In file included from lib\CurieBLE\src\CurieBLE.h:33:0,
                 from lib\CurieBLE\src\BLECentral.cpp:20:
lib\CurieBLE\src\BLECommon.h:26:54: fatal error: ../src/services/ble_service/ble_protocol.h: No such file or directory
compilation terminated.
*** [.pio\build\esp32doit-devkit-v1\libda2\CurieBLE\BLECentral.cpp.o] Error 1
In file included from lib\CurieBLE\src\./internal/BLEAttribute.h:23:0,
                 from lib\CurieBLE\src\BLEDescriptor.cpp:21:
lib\CurieBLE\src/BLECommon.h:26:54: fatal error: ../src/services/ble_service/ble_protocol.h: No such file or directory
compilation terminated.
In file included from lib\CurieBLE\src\CurieBLE.h:33:0,
                 from lib\CurieBLE\src\BLECharacteristic.cpp:22:
lib\CurieBLE\src\BLECommon.h:26:54: fatal error: ../src/services/ble_service/ble_protocol.h: No such file or directory
compilation terminated.
*** [.pio\build\esp32doit-devkit-v1\libda2\CurieBLE\BLECharacteristic.cpp.o] Error 1
*** [.pio\build\esp32doit-devkit-v1\libda2\CurieBLE\BLEDescriptor.cpp.o] Error 1
======================================================================================== [FAILED]

Why didn’t I get what you got?

I want to amend my first statements. It’s not the case that it clearly doesn’t work.

It doesn’t work clearly.

I guess this one has been resolved by now by deleting the .pio folder. Right?

No. Still doesn’t check. But we’re in ROI territory. I think some of my other problems illustrate my problems better. I’ll can’t worry about making bluetooth work when I can’t get the IDE to work.

It’s a pain,because everything I start gives me another problem to ask about. Seriously, I typed in a C++ code from a textbook, and it says it doesn’t have iostream.

I think I’ve learned all I can from this thread, so let’s abandon it.