CmpSymbol - Haskell

Welcome to the Functional Programming Zulip Chat Archive. You can join the chat here.

TheMatten
GHC.TypeLits Data.Ord> :k! CmpSymbol "a" "\000"
CmpSymbol "a" "\000" :: Ordering
= 'LT
GHC.TypeLits Data.Ord> compare "a" "\000"
GT

???

TheMatten

Tracking this down through GHC, it seems like it ends up being ByteString comparison (inside of FastString) - but

Data.ByteString Data.Ord> compare @ByteString "a" "\000"
GT
Fintan Halpenny

Could it be something stupid like the arguments are flipped?

TheMatten
Data.ByteString Data.Ord GHC.TypeLits> :k! CmpSymbol "a" "b"
CmpSymbol "a" "b" :: Ordering
= 'LT
Data.ByteString Data.Ord GHC.TypeLits> compare @ByteString "a" "b"
LT
Fintan Halpenny

Hmmm I wonder if "\000" is getting interpreted differently

Fintan Halpenny

Like for CmpSymbol it's the null character but for compare it's "\" followed by "0"s

Fintan Halpenny

Although, looking at an ascii table they're both LT 'a'

TheMatten

"\0" behaves the same way
And

λ> symbolVal $ Proxy @"\0"
"\NUL"
Fintan Halpenny

Think you have a bug on your hands

TheMatten

But I have no idea how can it arise :sweat_smile:

TheMatten

Just for completeness:

λ> :k! CmpSymbol "a" "\NUL"
CmpSymbol "a" "\NUL" :: Ordering
= 'LT
Fintan Halpenny

That's also wrong, right? :sweat_smile:

TheMatten

Nice: https://gitlab.haskell.org/ghc/ghc/-/issues/18562#note_293330

## Summary Compared to behaviour of e.g. `Ord String` or `Ord ByteString`, `CmpSymbol` treats string `"\0"` as bigger than e.g. `"a"`, even though null character appears as first in ASCII...
TheMatten

Thanks to @hsyl20 for tackling this quickly