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

Update to dprint 0.18.0 and latest swc #5509

Merged
merged 5 commits into from
May 17, 2020

Conversation

dsherret
Copy link
Member

@dsherret dsherret commented May 16, 2020

Closes #5180.

Also fixes swc parsing and formatting for template literals in types (ex. export type Permission = `test`;).

@@ -69,6 +69,21 @@ impl Into<TsTypeDef> for &TsLitType {
boolean: None,
},
),
TsLit::Tpl(tpl) => {
// A template literal in a type is not allowed to have
// expressions, so there will only be one quasi.
Copy link
Member Author

Choose a reason for hiding this comment

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

I'm not sure if quasi is the singular form of quasis... I'm not so familiar with the word quasis other than seeing it in the babel ast and in swc.


let param_def = match param {
Pat(pat) => pat_to_param_def(pat),
Param(param) => pat_to_param_def(&param.pat),
Copy link
Member Author

@dsherret dsherret May 16, 2020

Choose a reason for hiding this comment

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

This changed to support decorators on parameters.

My test suite in dprint had lots of failing tests after this change because a lot of code was looking for a Pat instead of Param, so hopefully my tests suite is thorough enough... still want to eventually add many repos to format in a test suite to find regressions.

@@ -25,7 +25,7 @@ pub fn function_to_function_def(
let mut params = vec![];

for param in &function.params {
let param_def = pat_to_param_def(param);
let param_def = pat_to_param_def(&param.pat);
Copy link
Member Author

Choose a reason for hiding this comment

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

+1 for the ParamDef and similar abstractions 🙂

@dsherret dsherret marked this pull request as ready for review May 16, 2020 18:07
@piscisaureus
Copy link
Member

piscisaureus commented May 16, 2020

I have a problem with this which is that it causes stack overflows in debug builds (windows).
Not your typical, "oops, infinite recursion" kind of stack overflow, but actually using too much stack.

To reproduce:

deno bundle --unstable --importmap cli/tests/bundle_im.json file:///D:/deno/cli/tests/bundle_im.ts

Edit:

It seems that this is actually happing with the swc 0.21.10: https://gist.github.com/piscisaureus/ae0d8a287d0a74ab80c459265c24cfb9#file-stack_overflow_swc-0-21-10-txt

Also with swc 0.22.0: https://gist.github.com/piscisaureus/ae0d8a287d0a74ab80c459265c24cfb9#file-stack_overflow_swc-0-22-0-txt

@dsherret
Copy link
Member Author

dsherret commented May 16, 2020

@piscisaureus I have the same problem on Windows in debug builds.

This issue is probably related, but in the case you mentioned it starts parsing with more in the stack: swc-project/swc#716

@piscisaureus
Copy link
Member

This issue is probably related, but in the case you mentioned it starts parsing with more in the stack: swc-project/swc#716

SWC still fills pretty much the entire stack (925kb out of 1mb) though...

# deno.exe!__chkstk() Line 109 (d:\agent\_work\2\s\src\vctools\crt\vcstartup\src\misc\amd64\chkstk.asm:109)
# (top of the stack)
RSP 0x4ff3a07988
RBP 0x4ff3a07a30

↕ 925 kB

# deno.exe!swc_ecma_parser::parser::Parser<swc_ecma_parser::parser::input::Capturing<swc_ecma_parser::lexer::Lexer<swc_common::input::SourceFileInput>>>::parse_module<swc_ecma_parser::parser::input::Capturing<swc_ecma_parser::lexer::Lexer<swc_common::input::SourceFileInput>>>() Line 137 (c:\Users\BertBelder\.cargo\registry\src\github.com-1ecc6299db9ec823\swc_ecma_parser-0.22.0\src\parser\mod.rs:137)
RSP 0x4ff3aeedc0
RBP 0x4ff3aeee40

↕ 12 kB

# deno.exe!dprint_plugin_typescript::formatter::Formatter::format_text(std::path::PathBuf * self, str* file_path) Line 84 (c:\Users\BertBelder\.cargo\registry\src\github.com-1ecc6299db9ec823\dprint-plugin-typescript-0.18.1\src\formatter.rs:84)
RSP 0x4ff3af1bd0
RBP 0x4ff3af1cc0

↕ 56 kB

# ntdll.dll!RtlUserThreadStart() (Unknown Source:0)
# (base of the stack)
RSP 0x4ff3affc60
RBP 0

@dsherret
Copy link
Member Author

Wow, seems a little excessive... it's such a small file too. Perhaps @kdy1 would know.

I just tried profiling myself in visual studio, but it keeps failing with a non-helpful error message.

@piscisaureus
Copy link
Member

I made a list of all the stack frames ordered by size. Maybe it'll help identify the cause of the issue.

https://gist.github.com/piscisaureus/ae0d8a287d0a74ab80c459265c24cfb9#file-stack_frames_by_size-txt

@kdy1
Copy link

kdy1 commented May 17, 2020

@piscisaureus I started investigating it. Thank you for the details.

@kdy1
Copy link

kdy1 commented May 17, 2020

The issue will be fixed by swc-project/swc#776.

@piscisaureus Btw, how can I get a stack usage report?

@bartlomieju bartlomieju added the cli related to cli/ dir label May 17, 2020
@piscisaureus
Copy link
Member

@kdy1

@piscisaureus Btw, how can I get a stack usage report?

Well... IDK what the right way is... What I did is debug the failing test with vscode + lldb plugin (vadimcn.vscode-lldb).

Then when the program hits the stack overflow, I enter this in the debugger console:

settings set frame-format "${frame.sp}   frame #${frame.index}: ${ansi.fg.yellow}${frame.pc}${ansi.normal}{ ${module.file.basename}{\`${function.name-with-args}{${frame.no-debug}${function.pc-offset}}}}{ at ${ansi.fg.cyan}${line.file.basename}${ansi.normal}:${ansi.fg.yellow}${line.number}${ansi.normal}{:${ansi.fg.yellow}${line.column}${ansi.normal}}}{${function.is-optimized} [opt]}{${frame.is-artificial} [artificial]}\n"

Followed by:

bt 999

That produces a list with stack frames prefixed with their stack pointer.
Save the output to a file.
Then run this node.js script to compute the stack frame sizes:

let prev_sp;
let lines = require("fs")
  .readFileSync("stack.txt", "utf8")
  .split(/\r?\n/)
  .map(l => l.replace(/^[\* ]+/, ""))
  .map(l => /^0x([0-9a-zA-Z]+) (.*)$/.exec(l))
  .filter(Boolean)
  .map(([, sp, rest]) => {
    sp = parseInt(sp, 16);
    let delta = sp - (prev_sp ?? sp);
    prev_sp = sp;
    return `+${String(delta).padStart(7)} ${rest}`;
  })
  .sort()
  .reverse();
console.log(lines.join("\n"));

So ... it's a bit of work, and there might very well be an easier way that I don't know about.

@kdy1
Copy link

kdy1 commented May 17, 2020

@piscisaureus Wow, thanks!
Parser ate all of my stacks and as test suite aborts instead of panic, I had a really hard time debugging stack size issue...

@dsherret dsherret marked this pull request as draft May 17, 2020 14:20
@dsherret dsherret marked this pull request as ready for review May 17, 2020 14:27
@dsherret
Copy link
Member Author

dsherret commented May 17, 2020

@kdy1 I just upgraded and unfortunately the stack still overflows, but it's good to know we at least fixed the issue with the diagnostic.

I got the output of the bundle text that's failing to parse here: https://gist.github.com/dsherret/6d126bb543501894bf017dd58d5dc325

@kdy1
Copy link

kdy1 commented May 17, 2020

@dsherret Well, I forgot publishing swc_common.
Can you try it again?

@dsherret
Copy link
Member Author

@kdy1 that was it! I didn't notice the change was in swc_common.

Works perfectly now. Thanks! 🙂

Copy link
Member

@piscisaureus piscisaureus left a comment

Choose a reason for hiding this comment

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

Awesome, thanks @dsherret and @kdy1!

@piscisaureus
Copy link
Member

Testing locally, I can also confirm that the the stack overflow has been fixed.

@piscisaureus piscisaureus merged commit a054250 into denoland:master May 17, 2020
@dsherret dsherret deleted the update_dprint_0_18_and_Swc branch May 17, 2020 17:06
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
cli related to cli/ dir
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Deno fmt deletes constructor decorators
4 participants