Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Arduino context doesn't populate until full build or opening of additional sketch #6

Closed
earlephilhower opened this issue Sep 25, 2023 · 4 comments
Assignees
Labels
bug Something isn't working

Comments

@earlephilhower
Copy link

earlephilhower commented Sep 25, 2023

First of all, thank you very much for building this! I've been getting requests for some of the plugins used w/arduino-pico like the LittleFS uploader to be ported to IDE 2.x.

As part of the uploader we run some external commands (like you do w/the ESP exception decoder you ported) that depend on some of the build.xxx properties (i.e. how large a filesystem, where it's located, what upload port, etc.).

What I'm seeing is that when the IDE starts up and opens the sketch from last time, is that the arduinoContext only has three fields:

{
    "sketchPath": "/home/earle/Arduino/Blink_copy_20221005103501",
    "userDirPath": "/home/earle/Arduino",
    "dataDirPath": "/home/earle/.arduino15"
}

If I open another sketch (but not build it), or run a build on the automatically opened sketch, the context seems to fully populate:

{
    "sketchPath": "/home/earle/Arduino/Blink",
    "fqbn": "pico:rp2040:rpipico",
    "boardDetails": {
        "buildProperties": {
            "version": "3.6.0",
....
            "build.fqbn": "pico:rp2040:rpipico",
            "build.arch": "RP2040",
            "build.libpicow": "libpicow-noipv6-nobtc-noble.a",
            "build.libpicowdefs": "-DLWIP_IPV6=0 -DLWIP_IPV4=1",
            "build.debug_level": "",
            "build.f_cpu": "133000000L",
            "build.flags.optimize": "-Os",
            "build.flags.rtti": "-fno-rtti",
....
    "port": {
        "label": "/dev/ttyACM1",
        "address": "/dev/ttyACM1",
        "hardwareId": "E6614C775B6C7F31",
        "properties": {
            "pid": "0xf00a",
            "serialNumber": "E6614C775B6C7F31",
            "vid": "0x2e8a"
        },
        "protocol": "serial",
        "protocolLabel": "Serial Port (USB)"
    },
    "userDirPath": "/home/earle/Arduino",
    "dataDirPath": "/home/earle/.arduino15"
}

The uploader plugins don't have any need for a build before being run, but they do need properties like the port and the buildProperties to do their jobs.

Is there a way to make the arduinoContext force-update from an end-user of the extension? Or is there a way to update this extension to populate it?

MCVE extension.ts (basically helloworld from yo code):

// The module 'vscode' contains the VS Code extensibility API
// Import the module and reference it with the alias vscode in your code below
import * as vscode from 'vscode';
import type { ArduinoContext } from 'vscode-arduino-api';

// This method is called when your extension is activated
// Your extension is activated the very first time the command is executed
export function activate(context: vscode.ExtensionContext) {

	// Use the console to output diagnostic information (console.log) and errors (console.error)
	// This line of code will only be executed once when your extension is activated
	console.log('Congratulations, your extension "pico-littlefs-upload" is now active!');
	const arduinoContext: ArduinoContext = vscode.extensions.getExtension(
		'dankeboy36.vscode-arduino-api'
	  )?.exports;
	  if (!arduinoContext) {
		// Failed to load the Arduino API.
		console.log(`Failed to find IDE context`);
		return;
	  }
	  console.log('Got IDE context 5!');
	  // The command has been defined in the package.json file
	  // Now provide the implementation of the command with registerCommand
	  // The commandId parameter must match the command field in package.json
	  let disposable = vscode.commands.registerCommand('pico-littlefs-upload.uploadLittleFS', () => {
	 	// The code you place here will be executed every time your command is executed
		// Display a message box to the user
		let str = JSON.stringify(arduinoContext, null, 4);
		console.log(str);
	  });

	  context.subscriptions.push(disposable);

}

// This method is called when your extension is deactivated
export function deactivate() {}

--edit--more testing--

I also attempted to grab the context on each command invocation thinking maybe I got a static copy of the context at a "bad time" during plug in initialization. That seems to make no difference, though, and only by building or opening another sketch can I get the state properly for the auto-opened sketch

export function activate(context: vscode.ExtensionContext) {
	  let disposable = vscode.commands.registerCommand('pico-littlefs-upload.uploadLittleFS', () => {
		const arduinoContext: ArduinoContext = vscode.extensions.getExtension(
			'dankeboy36.vscode-arduino-api'
		  )?.exports;
		  if (!arduinoContext) {
			return;
		  }
		let str = JSON.stringify(arduinoContext, null, 4);
		console.log(str);
	  });
	  context.subscriptions.push(disposable);
}

--edit--even more testing--

The behavior is that the first auto-opened sketch does NOT get its data populated until a build. Switching from the auto-open sketch, to a different one, then back to the auto-opened sketch still does not give any additional fields. Only building populates its object.

@per1234 per1234 added the bug Something isn't working label Sep 26, 2023
@per1234 per1234 self-assigned this Sep 26, 2023
@earlephilhower
Copy link
Author

FWIW, ignoring the above I have a MVP (minimum viable product) level extension using this at https://github.com/earlephilhower/pico-littlefs-upload . So, thanks again @dankeboy36 !

It's still a WIP and took more time this afternoon than it looks (my first VS code extension, my first Typescript introduction). It's also probably the ugliest Typescript you've ever seen. 😭 The synchronous calls to the uploader take a long time and I really should learn how to make that async so the IDE doesn't freeze for 30 secs every time while it's sending.

@per1234
Copy link
Collaborator

per1234 commented Sep 26, 2023

Hi @earlephilhower. Thanks for your report.

This fault is caused by a bug in Arduino IDE (introduced by arduino/arduino-ide@69ae38e / arduino/arduino-ide#2165).

I am able to reproduce the fault of boardDetails not being populated when the board was selected on Arduino IDE startup when using the IDE builds from 69ae38effaf950ae6fba83617b08b1cc0bc0a40d up to the latest on main.

Fortunately a fix has already been prepared: arduino/arduino-ide#2233. I am not able to reproduce the problem using the tester build from that PR.

If you would like to give the fix a try, the tester builds are available from the "Assets" section of the build workflow run summary page here:

https://github.com/arduino/arduino-ide/actions/runs/6262068930?pr=2233#artifacts

It should also be in the nightly build of Arduino IDE within a matter of days.

Workaround

  1. Select any other board from the Tools > Board menu in Arduino IDE.
  2. Select the target board from the Arduino IDE menus once again.

Related: dankeboy36/esp-exception-decoder#10


I have a MVP (minimum viable product) level extension using this at https://github.com/earlephilhower/pico-littlefs-upload

Very cool!

@per1234 per1234 closed this as not planned Won't fix, can't repro, duplicate, stale Sep 26, 2023
@dankeboy36
Copy link
Owner

my first VS code extension, my first Typescript introduction

Very nice, @earlephilhower 💪

So, thanks again @dankeboy36 !

Thank you, too, for the other original (1.x) plugin implementations. By the way, I also started to work on something similar you've just done. I am happy to contribute to your project.


I have enabled discussion in this repo: https://github.com/dankeboy36/vscode-arduino-api/discussions. Feel free to share and help grow the community.

@earlephilhower
Copy link
Author

Looking at your own ESP32 repo, dankeboy36/fs-image@main...init, it seems like maybe there will need to be 2 separate uploaders anyway: one ESP32 and one Pico/ESP8266. Since I did the ESP8266 and the LittleFS implementation on both cores (and the upload methods) they're very similar (only ~20 lines of code differ between the two).

But since I never really got into the ESP32 I didn't realize their setup is so different (partitions/etc.)! Plus they seem to support a FAT variant and SPIFFS on-flash as well, so a generic FS uploader there needs to know how to run mkfs.fat (or equivalent) instead of only mklittlefs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

3 participants