Joey Eremondi
Joey Eremondi

Reputation: 8423

Ignoring certain types with respect to = in OCaml

I'm in a situation where I'm modifying an existing compiler written in OCaml. I've added locations to the AST of the compiled language, but it has cause a bunch of bugs, because equality checks that previously succeeded now fail when identical ASTs have a different location attached.

In particular, I'm seeing List.mem return false when it should return true, since it relies on equality.

I'm wondering, is there a way for me to specify that, for any two values of my location type, that = should always return true for any two values of this type?

It would be a ton of work to refactor the entire compiler to use a custom equality everywhere, particularly since many polymorphic functions rely on being able to use = on any type.

Upvotes: 1

Views: 70

Answers (2)

gsg
gsg

Reputation: 9377

What an annoying problem to have.

If you are desperate and willing to write a little C code you can change the representation of locations to Custom_tag blocks, which allow customising the behaviour of some of the polymorphic operations. It's a nasty solution, and I suggest you look hard for a better approach before resorting to this one.

One possibility is that most of the compiler does not use locations at all. If so, you might be able to get away with replacing every location in the AST with the same dummy location. That should allow equality to behave as if locations were not there at all. This is rather hacky, and may not be possible if passes later in the compiler make any use of location info.

The 'clean' solution is to define a sane equality operation for ASTs (or to derive one using ppx) and to change the code to use that. As you say, this would be a lot more work.

Upvotes: 1

Jeffrey Scofield
Jeffrey Scofield

Reputation: 66803

There's no existing OCaml mechanism to do what you want.

You can use ppx to write OCaml syntax extensions, and (as I understand it) the behavior can depend on types. So there's some chance you could get things working that way. But it wouldn't be as straightforward as what you're asking for. I suspect you would need to explicitly handle = and any standard functions (like List.mem) that use = implicitly. (Note that I have no experience with ppx.)

I found a description of PPX here: http://ocamllabs.io/doc/ppx.html

Many experienced OCaml programmers avoid the use of built-in polymorphic equality because its behavior is often surprising. So it might be worth converting to a custom comparison function after all.

Upvotes: 2

Related Questions