| // verify.h |
| |
| // 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: riley@google.com (Michael Riley) |
| // |
| // \file |
| // Function to verify an Fst's contents |
| |
| #ifndef FST_LIB_VERIFY_H__ |
| #define FST_LIB_VERIFY_H__ |
| |
| #include <fst/fst.h> |
| #include <fst/test-properties.h> |
| |
| |
| namespace fst { |
| |
| // Verifies that an Fst's contents are sane. |
| template<class Arc> |
| bool Verify(const Fst<Arc> &fst, bool allow_negative_labels = false) { |
| typedef typename Arc::Label Label; |
| typedef typename Arc::Weight Weight; |
| typedef typename Arc::StateId StateId; |
| |
| StateId start = fst.Start(); |
| const SymbolTable *isyms = fst.InputSymbols(); |
| const SymbolTable *osyms = fst.OutputSymbols(); |
| |
| // Count states |
| StateId ns = 0; |
| for (StateIterator< Fst<Arc> > siter(fst); |
| !siter.Done(); |
| siter.Next()) |
| ++ns; |
| |
| if (start == kNoStateId && ns > 0) { |
| LOG(ERROR) << "Verify: Fst start state ID unset"; |
| return false; |
| } else if (start >= ns) { |
| LOG(ERROR) << "Verify: Fst start state ID exceeds number of states"; |
| return false; |
| } |
| |
| for (StateIterator< Fst<Arc> > siter(fst); |
| !siter.Done(); |
| siter.Next()) { |
| StateId s = siter.Value(); |
| size_t na = 0; |
| for (ArcIterator< Fst<Arc> > aiter(fst, s); |
| !aiter.Done(); |
| aiter.Next()) { |
| const Arc &arc =aiter.Value(); |
| if (!allow_negative_labels && arc.ilabel < 0) { |
| LOG(ERROR) << "Verify: Fst input label ID of arc at position " |
| << na << " of state " << s << " is negative"; |
| return false; |
| } else if (isyms && isyms->Find(arc.ilabel) == "") { |
| LOG(ERROR) << "Verify: Fst input label ID " << arc.ilabel |
| << " of arc at position " << na << " of state " << s |
| << " is missing from input symbol table \"" |
| << isyms->Name() << "\""; |
| return false; |
| } else if (!allow_negative_labels && arc.olabel < 0) { |
| LOG(ERROR) << "Verify: Fst output label ID of arc at position " |
| << na << " of state " << s << " is negative"; |
| return false; |
| } else if (osyms && osyms->Find(arc.olabel) == "") { |
| LOG(ERROR) << "Verify: Fst output label ID " << arc.olabel |
| << " of arc at position " << na << " of state " << s |
| << " is missing from output symbol table \"" |
| << osyms->Name() << "\""; |
| return false; |
| } else if (!arc.weight.Member() || arc.weight == Weight::Zero()) { |
| LOG(ERROR) << "Verify: Fst weight of arc at position " |
| << na << " of state " << s << " is invalid"; |
| return false; |
| } else if (arc.nextstate < 0) { |
| LOG(ERROR) << "Verify: Fst destination state ID of arc at position " |
| << na << " of state " << s << " is negative"; |
| return false; |
| } else if (arc.nextstate >= ns) { |
| LOG(ERROR) << "Verify: Fst destination state ID of arc at position " |
| << na << " of state " << s |
| << " exceeds number of states"; |
| return false; |
| } |
| ++na; |
| } |
| if (!fst.Final(s).Member()) { |
| LOG(ERROR) << "Verify: Fst final weight of state " << s << " is invalid"; |
| return false; |
| } |
| } |
| uint64 fst_props = fst.Properties(kFstProperties, false); |
| if (fst_props & kError) { |
| LOG(ERROR) << "Verify: Fst error property is set"; |
| return false; |
| } |
| |
| uint64 known_props; |
| uint64 test_props = ComputeProperties(fst, kFstProperties, &known_props, |
| false); |
| if (!CompatProperties(fst_props, test_props)) { |
| LOG(ERROR) << "Verify: stored Fst properties incorrect " |
| << "(props1 = stored props, props2 = tested)"; |
| return false; |
| } else { |
| return true; |
| } |
| } |
| |
| } // namespace fst |
| |
| #endif // FST_LIB_VERIFY_H__ |