I am working on a program to consume Go source code and maintain a running state of that program as a user edits that source in an IDE. I have a working implementation that *loads* the program AST representation (inc. all imports and standard library) and runs it through a type checker, but my implementation is rudimentary (so much so that I'm hesitant to share the source at this point; it's not terribly readable right now). Once the program is loaded, I can do simple things such as locating where an Ident is declared, but I haven't worked through finding all references to an Ident yet. I have some fundamental questions before moving on to greater tasks (such as handling edits to the program files). I hope that some of the folks here can provide some insight.
1) My current implementation maintains a single `token.FileSet` for all files in the program, across all packages. Is this correct, or is it better to keep a file set per package? 2) Similar question for `types.Info`. I currently have a single instance that is shared among all packages, but the source code comments say that it holds data "for *a* type-checked package" (emphasis mine). Should I be keeping a single instance per package instead? 3) I am keeping a `types.Checker` per package, but even so, I can only check one package at a time. My program is highly concurrent, and as it turns out, one checker may consuming a package "A", while package "A"'s checker is processing some test files, which results in a concurrent read/write panic from a map. (I am checking files from `build.Package` in waves -- first all Go and Cgo files, then test files, and later I will add external test files.) Are there any strategies to improve concurrency here? I am thinking about keeping a `sync.RWMutex` per-package, which I would write-lock when a package is getting checked, and claim a read-lock when a package is returned from my `types.Importer` / `types.ImporterFrom` implementation. Does this seem like a reasonable strategy? 4) When going through the type checker, what is the relationship between * `type.Package` instances that are imported via my custom `types.Importer` / `types.ImporterFrom` implementation provides, * the non-package-local tokens & identifiers, * and the information that gets stored in the `types.Info`? The thing that I'm really trying to understand is, if I have a complete program representation, and an exported part of a Go source code file changes, what will be the impact on packages that consume it? I know that once I run the new file contents through `parser.ParseFile`, I will get a completely new `ast.File`, which I will have to type-check again to get a new `types.Package`. I don't want to walk the entire package dependency tree if a low-level package changes; are there ways to avoid that? Thanks for any insight. This is a pretty big & abstract subject matter to ask a bunch of questions about all at once, and I apologize if I'm breaking etiquette here. -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. For more options, visit https://groups.google.com/d/optout.