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

os, runtime: enable os.Stdin for baremetal target #2625

Merged
merged 1 commit into from
Jun 1, 2022
Merged

Conversation

sago35
Copy link
Member

@sago35 sago35 commented Feb 8, 2022

This PR enables os.Stdin for the baremetal target.

There are two items that need to be discussed and agreement.

  1. Can an os package import a machine package?
    • solved: Could not import machine package from os package. I used go:link instead.
  2. There are changes that will break compatibility
    • I've changed src/machine/uart.go and src/machine/usb.go, and the behavior changes significantly.
    • bufio.Scanner.Scan() will not work without this change (error message is multiple Read calls return no data or error)
    • This PR only adds os.Stdin, so there are no compatibility-breaking changes.

@sago35 sago35 requested a review from aykevl February 8, 2022 14:32
@@ -38,7 +39,7 @@ func NewFile(fd FileHandle, name string) *File {

// Read is unsupported on this system.
func (f stdioFileHandle) Read(b []byte) (n int, err error) {
return 0, ErrUnsupported
return machine.Serial.Read(b)
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe it would be better to change here without changing uart.go and usb.go.
I think it would be better to call runtime.Gosched(), but it can't be called from the machine package.

func (f stdioFileHandle) Read(b []byte) (n int, err error) {
	size := 0
	for size == 0 {
		size = machine.Serial.Buffered()
		runtime.Gosched()
	}
	return machine.Serial.Read(b)
}

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this proposal is much better

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Updated to reflect @kenbell's point.
The problem with using machine.UART has been separated in #2739.

@deadprogram
Copy link
Member

@kenbell
Copy link
Member

kenbell commented Feb 9, 2022

@sago35 if I read this correctly, it makes UART blocking on read whereas it was non-blocking before. I can see this breaking existing code.

it would be better to put the blocking behaviour outside of UART implementation?

@sago35
Copy link
Member Author

sago35 commented Feb 9, 2022

@kenbell
I also want to maintain compatibility as much as possible.
However, if you do not block it, bufio.Scanner.Scan will fail.
In other words, I believe that the standard Go blocks it.

@sago35
Copy link
Member Author

sago35 commented Feb 9, 2022

If we do not change uart or usbcdc, but only os.Stdin, the following problem occurs.
This will probably be very confusing.

// It works as expected.
scanner := bufio.NewScanner(os.Stdin)
// Not working as expected.
scanner := bufio.NewScanner(machine.Serial)

@sago35 sago35 force-pushed the baremetal-stdin branch 2 times, most recently from 49f4f50 to 1c5d5a8 Compare March 10, 2022 10:34
@sago35
Copy link
Member Author

sago35 commented Mar 13, 2022

@kenbell @deadprogram
I would be happy to talk more about os.Stdin in the following thread.
https://gophers.slack.com/archives/CN4R2DQV7/p1646872768911309

@sago35 sago35 force-pushed the baremetal-stdin branch 3 times, most recently from e19531f to 3c9db4a Compare March 28, 2022 23:39
@sago35 sago35 changed the title machine, os: enable os.Stdin for baremetal target os, runtime: enable os.Stdin for baremetal target Mar 28, 2022
@sago35
Copy link
Member Author

sago35 commented Mar 28, 2022

if I read this correctly, it makes UART blocking on read whereas it was non-blocking before. I can see this breaking existing code.
it would be better to put the blocking behaviour outside of UART implementation?

This PR only adds os.Stdin, so there are no compatibility-breaking changes.

@sago35
Copy link
Member Author

sago35 commented Mar 29, 2022

@kenbell @deadprogram
Compatibility issues have been resolved and are ready for review.
Changes impacting compatibility have been moved to #2739.

With this PR, the following code will work in both standard Go and tinygo-baremetal.
I would like to see this change merged, as it would considerably improve the efficiency of development in baremetal.

https://github.com/tinygo-org/tinygo/blob/cc3009b5c15e0772f9f62c3c0ff6789e2bb961cf/src/examples/echo2/echo2.go

@sago35 sago35 marked this pull request as ready for review March 29, 2022 11:22
@deadprogram
Copy link
Member

@ardnew @bgould any implications in this PR for the USB 2 work that is happening?

@ardnew
Copy link
Contributor

ardnew commented May 17, 2022

@ardnew @bgould any implications in this PR for the USB 2 work that is happening?

After a cursory review, I don't see any potential blockers with respect to the USB 2.0 package. But I'm still a little confused as to what we gain with this capability. Is this to create a type-safe, consistent IO interface? As opposed to the awkward juggling we are currently doing with Serial/UART/USB constants?

@sago35
Copy link
Member Author

sago35 commented May 17, 2022

What we get with this PR is support for os.Stdin.Read() on baremetal targets.
With this PR, what os.Stdin points to is machine.Serial.

But now I see that os.Stdin.ReadAt() is not implemented and should be added.
added: The implementation of os.Stdin.ReadAt() is covered in another PR.

old :

// Read is unsupported on this system.
func (f stdioFileHandle) Read(b []byte) (n int, err error) {
return 0, ErrUnsupported
}
func (f stdioFileHandle) ReadAt(b []byte, off int64) (n int, err error) {
return 0, ErrNotImplemented
}

@deadprogram
Copy link
Member

Any other feedback or comments before we merge this?

@deadprogram
Copy link
Member

Merging in order to keep this process with improvements for serial/USB communication moving along. Thanks @sago35

@deadprogram deadprogram merged commit 39805bc into dev Jun 1, 2022
@deadprogram deadprogram deleted the baremetal-stdin branch June 1, 2022 05:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants