Skip to content

isREPLconnected & isUSBconnected #544

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

Closed
ladyada opened this issue Jan 22, 2018 · 18 comments
Closed

isREPLconnected & isUSBconnected #544

ladyada opened this issue Jan 22, 2018 · 18 comments

Comments

@ladyada
Copy link
Member

ladyada commented Jan 22, 2018

could be handy to be able to query, from the python side, if USB is enumerated and/or the REPL is opened!

put down for 3.0 but can be long-term

@sommersoft
Copy link

I've been researching this between Travis battles. I think I've got USB mostly figured out, but still working on a plan for REPL. Initially I was hoping it could go into the micropython module. But, with USB being handled at the port level, somewhere in shared-bindings & common-hal is probably better. I imagine REPL will end up the same way, given the REPL flavors on different ports.

Here are my USB notes so far.

  • Atmel-SAMD: ports/atmel-samd/usb.c is an easy place to grab usb_connected(), which points to the CDC handlers.

  • ESP8266: ports/esp8266/machine_uart.c seems to me the only place to grab USB state by polling UART0. I don't understand ESP's USB fully yet, so this is just going off of my reading. I dug around ESP's SDK a little and didn't see anything else that jumped out at me.

  • nRF: seems similar to ESP8266 in needing to poll UART0. ports/nrf/hal/hal_uart.c has hal_uart_available().

For where to put the function calls, board seems the syntactic choice to me, but I understand not wanting to break from the "here lie the pins" approach. microcontroller would be my next guess. I defer to you all on that one.

I'm ok with being assigned on this one, but definitely not trying to block anyone out from doing it. I just wanted to document that I'm looking at it, and start the conversation on the particulars.

Lastly, please let me know if I'm way off in my approach. I'm well known for trying to make things more difficult than they actually are.

@tannewt
Copy link
Member

tannewt commented Feb 4, 2018

@sommersoft seems like you are headed the right direction! I think a new supervisor module and singleton would be best.

@sommersoft
Copy link

So, after a few more days crawling around the core, I think checking for a live REPL connection isn't currently possible. One exception to that is WebREPL; that would be doable by checking for the file stats. Of course I caveat all of this with "I am very possibly wrong", but here is how I've come to that conclusion.

  1. Starting at circuitpython/main.c:L#119, the boot code checks serial_connected(), and if it is, it prints out the startup info to the REPL. (there is at least one other place where the serial is checked before sending/listening to REPL...but it's all rapidly congealing inside my brain and I forgot where I saw it)

  2. serial_connected() is in circuitptyhon/ports/????/supervisor/serial.c for each port.

    • atmel-samd: serial_connected returns the result of usb_connected() (see above comment)
    • nrf: serial_connected() returns True...always. As in, it's hardcoded: return true; (L#66)
    • esp8266: actually uses it's own main.c which has a slightly different method, but it works the same by just checking for a serial connection. There is also the added use of WebREPL.

In summary, there is no active REPL state information; it all just assumes if the serial connection, through USB/BLE/Web, is active then we should send and listen for REPL activity.

I'll keep digging into it, but I think I've hit bedrock...

I've got USB check running on SAMD. I'll start working the others soon.

@tannewt
Copy link
Member

tannewt commented Feb 6, 2018

Use serial_connected to determine whether serial is connected. Rename isREPLconnected to isSerialConnected in your brain. Many folks confuse REPL with serial.

I think USB enumeration status would be a bit more difficult actually. I don't believe we track it at this point.

@sommersoft
Copy link

So, I'll press forward with just extending serial_connected to the python layer. I want to dig a little on the nRF port being hardcoded to return true;, though.

I started to look at checking/tracking USB enumeration...a bit out of my depth. That ASF4 stuff is seriously fragmented. Don't know how you and Dan deal with that on the regular...

@tannewt
Copy link
Member

tannewt commented Feb 9, 2018

The nRF may not be able to tell because it uses a separate USB to UART chip. The newer ones will do USB but this probably hasn't been updated for it.

Do a PR for the serial connection first and then do usb enumeration separately.

@sommersoft
Copy link

sommersoft commented Mar 10, 2018

After a slightly exhaustive dig into the ESP8266 UART realm, I have concluded that serial_connected will not be possible on ESP8266. My previous comment on "poll UART0" didn't pan out. Here is what I think I know:

  • UART is handled on chip, with serial going through the USB-to-UART.
  • UARTs are setup the same regardless of power supply situation.
  • The chip handles UART with interrupts, filling the FIFO on RX. The interrupt is switched off when reading the FIFO, then turned back on.
  • This means there is no active state, or way to check it. It would just be setting the state based on UART RX events (which could also come from the board.RX), which would only happen during REPL interaction. (coincidentally, that would give isREPLconnected state)

While we could just as easily return serial_connected = true all the time like nRF, I don't see the advantage to getting supervisor into ESP8266 when none of the other functions would be useful either (like future nRF could).

I can of course have my opinions changed or overridden.

@tannewt
Copy link
Member

tannewt commented Mar 12, 2018

@sommersoft I think I have it set up to wait for a character input before thinking its connected. Its not exact but good enough in my mind.

@tannewt tannewt modified the milestones: 3.0, 4.0 May 14, 2018
@tannewt tannewt modified the milestones: Bluetooth, Long term Jul 3, 2018
@No1089
Copy link

No1089 commented Oct 20, 2018

Hi,
Is this a function that works? (I'm getting the idea it doesn't)
I'm using an itsybitsy M0 with the atSAMD21 chip.
I have a problem with a PC USB port not switching off power and that was used to determine if other devices should be on/off.
isUSBconnected() would save a lot of hassle in this case.
Is it perhaps possible to see if the filesystem has been mounted by the PC OS?

@sommersoft
Copy link

@No1089 you can use the following to determine if a USB serial connection is established:

import supervisor
usb_status = supervisor.runtime.serial_connected()

Since USB status is detected based on a serial connection, we named the function according to that.

Here is a link to the documentation: https://circuitpython.readthedocs.io/en/3.x/shared-bindings/supervisor/Runtime.html#supervisor.Runtime

@No1089
Copy link

No1089 commented Oct 20, 2018

@sommersoft I considered using serial_connected(), but the PC does not have a serial connection running, so would it still work?
The problem is the exhibit this is in, is 1800km away and I don't have access to a CircuitPy device until Monday. Thus I can't test my hypotheses.

@sommersoft
Copy link

@No1089, is it connected to the PC using a data-capable USB cable? You asked about checking if the filesystem has been mounted by the PC, which leads me to believe that it is. serial_connected() is based on the USB connection to the PC. It doesn't require that a separate serial terminal/program is running. Also, as is noted in the documentation, a USB disconnect after initial connect doesn't change the state of serial_connected(). It just isn't supported with the backend firmware.

If it isn't connected with a data cable, but rather a charge only cable, then no serial_connected() won't work. This is due to no USB serial connection being established with the PC. In this case, I'm not sure how you could approach detecting PC power state. Maybe an external voltage regulator inline from a GPIO to the motherboard to detect power state?

@dhalbert
Copy link
Collaborator

dhalbert commented Oct 20, 2018

@No1089 If you're mostly trying to determine whether USB power is being supplied or not (as opposed to a serial conenction being present), you could put a voltage divider (two series resistors) between the USB voltage pin and ground, and connect the middle to a pin set to be an analog input. Measure the voltage on the pin.The voltage divider could be two equal resistors (say 100k each), so the voltage would be 2.5V if USB is connected, and 0V if not.

You need the voltage divider because the max voltage on an analog pin is 3.3V. It would be damaged by 5V.

@sommersoft
Copy link

Thanks @dhalbert. Totally forgot about using the USB power pin...

@No1089
Copy link

No1089 commented Oct 22, 2018

@sommersoft Thanks. I'll look into it. There is a button input that I'll poll for a couple of seconds and then do a reset before checking serial_connected() again - will this work? The device remains powered externally to enable it to detect the PC power state, so I would need to force a restart.
@dhalbert I'm using the USB power pin with a MosFET to check power (This has always worked fine), but the motherboard keeps feeding power to USB, and there is no setting in BIOS to turn it off. Smart devices don't charge, but the itsybitsy m0 still gets power. A hardware solution is the easiest, but I'm 10000 miles away.

@dhalbert
Copy link
Collaborator

@No1089 You may know this already, but you can force a reset with microcontroller.reset(): https://circuitpython.readthedocs.io/en/3.x/shared-bindings/microcontroller/__init__.html

@sommersoft sommersoft removed their assignment Aug 15, 2019
@sommersoft sommersoft added the Hacktoberfest Beginner friendly issues for Hacktoberfest event label Oct 1, 2019
@adafruit-adabot adafruit-adabot removed the Hacktoberfest Beginner friendly issues for Hacktoberfest event label Nov 2, 2019
@dhalbert
Copy link
Collaborator

I think these are both covered now by supervisor.runtime.serial_connected and supervisor.runtime.usb_connected.

@ladyada
Copy link
Member Author

ladyada commented Mar 19, 2021

yay for closing our oldest issue!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

6 participants