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

Unexpected behaviour when setting tab stops #140

Closed
j4james opened this issue Mar 21, 2018 · 2 comments
Closed

Unexpected behaviour when setting tab stops #140

j4james opened this issue Mar 21, 2018 · 2 comments
Assignees
Labels
Product-Conhost For issues in the Console codebase Work-Item It's being tracked by an actual work item internally. (to be removed soon)
Milestone

Comments

@j4james
Copy link
Collaborator

j4james commented Mar 21, 2018

  • Your Windows build number:

Microsoft Windows [Version 10.0.16299.309]

  • What you're doing and what's happening:

I've been experimenting with the various escape sequences for setting tab stops and noticed a number of areas in which the behaviour is different from what I would have expected. This seems largely due to the fact that the default tab stops are treated differently from the manually specified tabs.

If you start with just the default tab stops (every 8 columns), and try to use the single-column tab clear command (TBC) to clear one of those tabs, it appears to have no effect in the Windows console. Example test case:

printf "\033[3g\033c|\t|\t|\n\t\033[0g\r\tx\n"

In a Linux console, the TBC clears the tab stop at column 8 (zero-based), so the x appears in column 16 as expected:

|       |       |
                x

In the Windows 10 console, though, the TBC command has no effect, so the x appears in column 8:

|       |       |
        x

The horizontal tab set (HTS) command is similarly out of sync with the default tab stops. So if you start with the defaults, and try to set an addition tab with HTS, that one tab stop appears to wipe out all the defaults. Example test case:

printf "\033[3g\033c|\t|\t|\n    \033H\r\tx\tx\n"

In a Linux console this adds a tab stop in column 4, leaving the default 8 column tabs unchanged, so you get one x in column 4 and one in column 8:

|       |       |
    x   x

In the Windows 10 console, the defaults are erased, so while the first x appears in column 4, the second x appears in the rightmost column of the display:

|       |       |
    x                                                       x

Then there's the all-column TBC, which is supposed to clear all tab stops, but just resets to the defaults in the Windows console. Example test case:

printf "\033[3g\033c|\t|\t|\n\033[3g\tx\n"

On Linux this works as expected - all tabs are cleared, so the x appears in the rightmost column of the display:

|       |       |
                                                            x

On Windows the tabs are reset to the default positions, so the x appears in column 8:

|       |       |
        x

Now if I really did want to reset the tabs to their defaults, I would have expected the ESC c (reset) command to have that effect, but in the Windows console that leaves the most recently set tab stops unchanged. Example test case:

printf "\033[3g\033c    \033H\033c|       |       |\n\tx\n"

This sequence sets a tab in column 4, resets the terminal with ESC c, then attempts to output an x in the first tab position. On Linux the tabs are reset to the 8 column defaults, so the x appears in column 8:

|       |       |
        x

On Windows the tab stop in column 4 is retained, even after the reset, so the x appears in column 4:

|       |       |
    x

Note that in all of these test cases I'm starting with a combination of CSI 3g and ESC c as a cross platform way to reset the tabs before getting to the actual test. If you wanted to be certain of the behaviour, though, it would be preferable to test each sequence from a fresh console.

I should also note there are a few other areas where the tab functionality differs from what I would expect, but I thought it best to check first whether the current behaviour is intentionally the way it is, in which case my other complaints would likely be non-issues too.

  • What's wrong / what should be happening instead:

I'd expect the default tab stops and manual specified tab stops to work in exactly the same way, exhibiting behaviour more in line with what I see in a Linux console. I'd also expect the reset command to reset the tab stops to their default values.

@zadjii-msft
Copy link
Member

Boy, there's a lot going on here, isn't there.

Almost all of this comes down to the incompatibilities between the legacy tab stops (at every 8 columns) and the way linux-like tab stops are set. We have to try and maintain back-compat with apps that don't understand VT, so if one app sets a bunch of tab stops, it doesn't mess up a later launched windows executable that doesn't understand that and just tabs around blindly.

That being said, I'll file a bug for me to come back and try and make sure it's all consistent.

@zadjii-msft zadjii-msft self-assigned this Mar 28, 2018
@zadjii-msft zadjii-msft added Work-Item It's being tracked by an actual work item internally. (to be removed soon) Product-Conhost For issues in the Console codebase labels Mar 28, 2018
@zadjii-msft zadjii-msft added this to the RS5 milestone Mar 28, 2018
@adiviness adiviness added the Resolution-Fix-Committed Fix is checked in, but it might be 3-4 weeks until a release. label Jul 19, 2018
@DHowett-MSFT
Copy link
Contributor

It looks like this went out with 1809. Thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Product-Conhost For issues in the Console codebase Work-Item It's being tracked by an actual work item internally. (to be removed soon)
Projects
None yet
Development

No branches or pull requests

4 participants