This patch allows Resolve to use more static diagnostic factories. Resolution 
errors support generation of diagnostics. This generation is very flexible and 
allows creating either a toplevel (error or warning) diagnostic, or a nested 
(fragment) diagostic. To support this, many resolution diagnostics in javac 
define some "overloads" in compiler.properties - e.g.


# 0: message segment
compiler.err.prob.found.req=...
# 0: message segment
compiler.misc.prob.found.req=...
# 0: message segment, 1: type, 2: type
compiler.warn.prob.found.req=...


To support switching from one diagnostic kind to another, this patch adds a new 
method on `DiagnosticInfo`, namely `toType(DiagnosticType)`. The default 
implementation of this method will simply check that the type is identical to 
that of the current diagnostic info, and throw otherwise.

This patch modifies the build-time step to construct diagnostic factories, so 
that, whenever a diagnostic overload is detected, the `toType` method is 
overridden, and the right constants/factories are returned/called depending on 
the requested diagnostic type. For instance, the factory for the 
`prob.found.req` key will look as follows in the generated code:


/**
         * compiler.err.prob.found.req=\
         *    incompatible types: {0}
         */
        public static Error ProbFoundReq(Fragment arg0) {
            return new Error("compiler", "prob.found.req", arg0) {
                public JCDiagnostic.DiagnosticInfo 
toType(JCDiagnostic.DiagnosticType kind) {
                    return switch (kind) {
                        case ERROR -> this;
                        case WARNING -> throw new AssertionError("Unsupported 
kind: " + kind);
                        case FRAGMENT -> Fragments.ProbFoundReq(arg0);
                        case NOTE -> throw new AssertionError("Unsupported 
kind: " + kind);
                    };
                }
            };
        }


As you can see, the build time process correctly detects all diagnostic 
overloads and generate some code to convert one diagnostic info to another. 
Note that in this case, only two overloads are detected (`err` and `misc`), 
given that `warn` has a different type comment so not, technically speaking, an 
overload.

With this support it is relatively easy to go back to Resolve and update most 
of the resolution errors to use the generated factories.

The only case I have not dealt with is the "cannot.resolve" diagnostic, which 
has many variants: `{ var, method, generic method } x { location, no location 
}`. To use the factories effectively here a change in the way the diagnostic is 
structured is required, but doing so, while trivial, will cause many change in 
the golden test files, so I held off these changes for now, and will come back 
later to this.

-------------

Commit messages:
 - Add newlines after factory method/field declaration
 - Simplify code in Resolve
 - Tweak ClassGenerator
 - Merge branch 'master' into resolve_error_diags
 - Polish properties generation code
 - Kind of works
 - Sharpen signature of compiler.properties
 - Initial cleanup; some issues:

Changes: https://git.openjdk.java.net/jdk/pull/4089/files
 Webrev: https://webrevs.openjdk.java.net/?repo=jdk&pr=4089&range=00
  Issue: https://bugs.openjdk.java.net/browse/JDK-8267312
  Stats: 248 lines in 6 files changed: 109 ins; 37 del; 102 mod
  Patch: https://git.openjdk.java.net/jdk/pull/4089.diff
  Fetch: git fetch https://git.openjdk.java.net/jdk pull/4089/head:pull/4089

PR: https://git.openjdk.java.net/jdk/pull/4089

Reply via email to