code: protected String calculateTableForMany(ToMany property, String sessionFactoryBeanName) {
          NamingStrategy namingStrategy = getNamingStrategy(sessionFactoryBeanName);
  
          String propertyColumnName = namingStrategy.propertyToColumnName(property.getName());
          //fix for GRAILS-5895
          PropertyConfig config = getPropertyConfig(property);
          JoinTable jt = config != null ? config.getJoinTable() : null;
          boolean hasJoinTableMapping = jt != null && jt.getName() != null;
          String left = getTableName(property.getOwner(), sessionFactoryBeanName);
  
          if (Map.class.isAssignableFrom(property.getType())) {
              if (hasJoinTableMapping) {
                  return jt.getName();
              }
              return addUnderscore(left, propertyColumnName);
          }
  
          if (property instanceof Basic) {
              if (hasJoinTableMapping) {
                  return jt.getName();
              }
              return addUnderscore(left, propertyColumnName);
          }
  
          if (property.getAssociatedEntity() == null) {
              throw new MappingException("Expected an entity to be associated with the association ("  + property + ") and none was found. ");
          }
  
          String right = getTableName(property.getAssociatedEntity(), sessionFactoryBeanName);
  
          if (property instanceof ManyToMany) {
              if (hasJoinTableMapping) {
                  return jt.getName();
              }
              if (property.isOwningSide()) {
                  return addUnderscore(left, propertyColumnName);
              }
              return addUnderscore(right, namingStrategy.propertyToColumnName(((ManyToMany) property).getInversePropertyName()));
          }
  
          if (shouldCollectionBindWithJoinColumn(property)) {
              if (hasJoinTableMapping) {
                  return jt.getName();
              }
              left = trimBackTigs(left);
              right = trimBackTigs(right);
              return addUnderscore(left, right);
          }
  
          if (property.isOwningSide()) {
              return addUnderscore(left, right);
          }
          return addUnderscore(right, left);
      }
docs: Calculates the mapping table for a many-to-many. One side of
  the relationship has to "own" the relationship so that there is not a situation
  where you have two mapping tables for left_right and right_left