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

Highlighting error when defining global variables with construction functions #282

Closed
Dust1404 opened this issue Jul 3, 2019 · 8 comments
Labels
🐛 Bug Something isn't working High Priority Common or breaks highlighting of more than just itself

Comments

@Dust1404
Copy link

Dust1404 commented Jul 3, 2019

VSCode 1.35.1
Better C++ Syntax 1.12.11

similar to #206

1
2

#include <ctime>
#include <cstdio>
#include <random>

std::mt19937 eng1(std::time(nullptr));
// std::mt19937 eng2(1234);
// int n(1234);
// 3 lines above can all cause the problem

int main()
{
	printf("Hello World!\n");

	return 0;
}
@matter123 matter123 added High Priority Common or breaks highlighting of more than just itself 🐛 Bug Something isn't working 🔍 investigating More information is being gathered labels Jul 3, 2019
@matter123
Copy link
Collaborator

So to summarize this issue:

  • function calls inside of potential function definitions cause the paramaters to not end at the second )
  • literals are not highlighted and cause the same issue.

@matter123
Copy link
Collaborator

matter123 commented Jul 3, 2019

@jeff-hykin When there is an ambiguity between a function definition and a constructor call should the highlighting of A foo(A,B,C) as entity.name.type.parameter be disabled?

@matter123
Copy link
Collaborator

matter123 commented Jul 3, 2019

@jeff-hykin It should be possible to first try matching a single line to look for a valid function definition and fall back on the pattern-range only if the definition spread across more than one line? That should make it possible to detect that void *foo(nullptr); is not a function definition.

@jeff-hykin jeff-hykin added the Hard label Jul 3, 2019
@jeff-hykin
Copy link
Owner

jeff-hykin commented Jul 3, 2019

You probably already know this stuff @matter123 , I'm going to summarize it for myself and others though.

Multi-line case

Fundamentally, this issue is that there's no pattern for function initializations.

aType aThing(     // this is a function
    int a
);
aType aThing(    // this is an initialization 
    "testing"
);

Textmate can only look at one line before irreversibly jumping into a range. Right now when it sees aType aThing( it irreversibly jumps into the function-definition range. There is no way for the grammar to know if its a function or a multi-line initialization until after the first line, this is fundamentally not solvable in the textmate grammar. (However, the tree-sitter parser could handle this).

All one line cases

int thing1(thing2); // a prototype function if thing2 is a type
int thing1(thing2); // an initialization if thing2 is a variable
Textmate (and also the tree-sitter-parser) has no way of knowing if thing2 is a type or a variable.
This is unsolvable without a language specific parser/server.

Special cases of one liners

int *aVar(nullptr);
string aVar("test");
string aVar( aType{"test"} );
SomeType aVar(variable1, variable2, "test");
SomeType aVar(variable1, variable2, "test", aType{ aType{"test"}, "test"} );
This, as @matter123 mention is possible to detect. There only needs to be one literal value or one initialization that contains a literal value. However, while the first case is trivial, the cases become increasingly non-trival to the point of extreme complexity by the 5th example.

The makeshift solution (then old and probably future answer)

Rather than knowing if it actually is a function call or an initialization, its possible to pretend that it is always both, and then highlight things accordingly. The reason this isn't working right now is because, in order to make the parameters be highlighted better, some assumptions were made that are perfectly valid for function definitions. However, those assumptions are screwing up inside of initializations.

I'm going to try to make a partial fix to make this problem not cascade beyond the initialization parentheses. I'll close this issue once that is fixed. However, I'll create another issue for the more general problem, including deciding how to tag the ambiguous A foo(A,B,C).

jeff-hykin added a commit that referenced this issue Jul 3, 2019
@jeff-hykin
Copy link
Owner

jeff-hykin commented Jul 3, 2019

Fixed an pushed with v1.12.13 including the problems with curly brace initializations like Atype aVar(Atype{1,2,3});

@jeff-hykin jeff-hykin removed Hard 🔍 investigating More information is being gathered labels Jul 4, 2019
@Dust1404
Copy link
Author

Dust1404 commented Jul 4, 2019

The problem still exists in v1.12.14.

1
2
3

mt19937 gen(time(nullptr) ^ (size_t) new char);
// mt19937 gen(1234);
// mt19937 gen(time(nullptr));

inline int randint(int l, int r)
{
	return uniform_int_distribution<>(l, r)(gen);
}

int main()
{
	for (int i = 1; i <= N; ++i)
		R[i] = randint(0, 100) & 31;

	return 0;
}

@matter123
Copy link
Collaborator

The main issue has been fixed in v1.12.15. There is an issue with the highlighting of size_t, Ill file a separate issue.

@jeff-hykin
Copy link
Owner

@Dust1404 let me know if you find any more cases. I'm pretty confident this most recent change will have covered all of them.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
🐛 Bug Something isn't working High Priority Common or breaks highlighting of more than just itself
Projects
None yet
Development

No branches or pull requests

3 participants