Basically, I just split on "*” and then do substring searches while making sure that the substrings are in order and don’t overlap.
I also noticed that matches doesn’t normalize strings to lowercase, and it seems like LDAP searches are case-insensitive, so that may be needed.
Also, matches seems to work on accident in cases were attribute values are single-value strings. That is, len(values) > 0 is true for both a list and a string, and self.value in values does a substring search if values is a string, so that also works.
Case-sensitivity varies by attribute and theoretically by server. In fact, each attribute may have not just one, but three separate matching rules: for equality, ordering, and substrings. Many standard matching rules are defined, but I imagine a server would be free to implement any arbitrary algorithm it wanted.
It would probably make sense for mockldap to exhibit correct behavior for the standard schemas. It would likely be a tedious project of moderate size.