
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
// Copyright 2005-2010 Google, Inc.
// Author: jpr@google.com (Jake Ratkiewicz)

// This file defines the registration mechanism for new operations.
// These operations are designed to enable scripts to work with FST classes
// at a high level.

// If you have a new arc type and want these operations to work with FSTs
// with that arc type, see below for the registration steps
// you must take.

// These methods are only recommended for use in high-level scripting
// applications. Most users should use the lower-level templated versions
// corresponding to these.

// If you have a new arc type you'd like these operations to work with,
// use the REGISTER_FST_OPERATIONS macro defined in fstcsript.h

// If you have a custom operation you'd like to define, you need four
// components. In the following, assume you want to create a new operation
// with the signature
//
//    void Foo(const FstClass &ifst, MutableFstClass *ofst);
//
//  You need:
//
//  1) A way to bundle the args that your new Foo operation will take, as
//     a single struct. The template structs in arg-packs.h provide a handy
//     way to do this. In Foo's case, that might look like this:
//
//       typedef args::Package<const FstClass &,
//                             MutableFstClass *> FooArgs;
//
//     Note: this package of args is going to be passed by non-const pointer.
//
//  2) A function template that is able to perform Foo, given the args and
//     arc type. Yours might look like this:
//
//       template<class Arc>
//       void Foo(FooArgs *args) {
//          // Pull out the actual, arc-templated FSTs
//          const Fst<Arc> &ifst = args->arg1.GetFst<Arc>();
//          MutableFst<Arc> *ofst = args->arg2->GetMutableFst<Arc>();
//
//          // actually perform foo on ifst and ofst...
//       }
//
//  3) a client-facing function for your operation. This would look like
//     the following:
//
//     void Foo(const FstClass &ifst, MutableFstClass *ofst) {
//       // Check that the arc types of the FSTs match
//       if (!ArcTypesMatch(ifst, *ofst, "Foo")) return;
//       // package the args
//       FooArgs args(ifst, ofst);
//       // Finally, call the operation
//       Apply<Operation<FooArgs> >("Foo", ifst->ArcType(), &args);
//     }
//
//  The Apply<> function template takes care of the link between 2 and 3,
//  provided you also have:
//
//  4) A registration for your new operation, on the arc types you care about.
//     This can be provided easily by the REGISTER_FST_OPERATION macro in
//     operations.h:
//
//       REGISTER_FST_OPERATION(Foo, StdArc, FooArgs);
//       REGISTER_FST_OPERATION(Foo, MyArc, FooArgs);
//       // .. etc
//
//
//  That's it! Now when you call Foo(const FstClass &, MutableFstClass *),
//  it dispatches (in #3) via the Apply<> function to the correct
//  instantiation of the template function in #2.
//


#ifndef FST_SCRIPT_SCRIPT_IMPL_H_
#define FST_SCRIPT_SCRIPT_IMPL_H_

//
// This file contains general-purpose templates which are used in the
// implementation of the operations.
//

#include <utility>
using std::pair; using std::make_pair;
#include <string>

#include <fst/script/fst-class.h>
#include <fst/generic-register.h>
#include <fst/script/arg-packs.h>

#include <fst/types.h>

namespace fst {
namespace script {

//
// A generic register for operations with various kinds of signatures.
// Needed since every function signature requires a new registration class.
// The pair<string, string> is understood to be the operation name and arc
// type; subclasses (or typedefs) need only provide the operation signature.
//

template<class OperationSignature>
class GenericOperationRegister
    : public GenericRegister<pair<string, string>,
                             OperationSignature,
                             GenericOperationRegister<OperationSignature> > {
 public:
  void RegisterOperation(const string &operation_name,
                         const string &arc_type,
                         OperationSignature op) {
    this->SetEntry(make_pair(operation_name, arc_type), op);
  }

  OperationSignature GetOperation(
      const string &operation_name, const string &arc_type) {
    return this->GetEntry(make_pair(operation_name, arc_type));
  }

 protected:
  virtual string ConvertKeyToSoFilename(
      const pair<string, string>& key) const {
    // Just use the old-style FST for now.
    string legal_type(key.second);  // the arc type
    ConvertToLegalCSymbol(&legal_type);

    return legal_type + "-arc.so";
  }
};


// Operation package - everything you need to register a new type of operation

// The ArgPack should be the type that's passed into each wrapped function -
// for instance, it might be a struct containing all the args.
// It's always passed by pointer, so const members should be used to enforce
// constness where it's needed. Return values should be implemented as a
// member of ArgPack as well.

template<class ArgPack>
struct Operation {
  typedef ArgPack Args;
  typedef void (*OpType)(ArgPack *args);

  // The register (hash) type
  typedef GenericOperationRegister<OpType> Register;

  // The register-er type
  typedef GenericRegisterer<Register> Registerer;
};


// Macro for registering new types of operations.

#define REGISTER_FST_OPERATION(Op, Arc, ArgPack)                        \
  static fst::script::Operation<ArgPack>::Registerer                \
  arc_dispatched_operation_ ## ArgPack ## Op ## Arc ## _registerer(     \
      make_pair(#Op, Arc::Type()), Op<Arc>)


//
// Template function to apply an operation by name
//

template<class OpReg>
void Apply(const string &op_name, const string &arc_type,
           typename OpReg::Args *args) {
  typename OpReg::Register *reg = OpReg::Register::GetRegister();

  typename OpReg::OpType op = reg->GetOperation(op_name, arc_type);

  if (op == 0) {
    FSTERROR() << "No operation found for \"" << op_name << "\" on "
               << "arc type " << arc_type;
    return;
  }

  op(args);
}


// Helper that logs to ERROR if the arc types of a and b don't match.
// The op_name is also printed.
bool ArcTypesMatch(const FstClass &a, const FstClass &b,
                   const string &op_name);

}  // namespace script
}  // namespace fst

#endif  // FST_SCRIPT_SCRIPT_IMPL_H_
