KiCad PCB EDA Suite
Loading...
Searching...
No Matches
sch_io_lib_cache.cpp
Go to the documentation of this file.
1/*
2 * This program source code file is part of KiCad, a free EDA CAD application.
3 *
4 * Copyright The KiCad Developers, see AUTHORS.txt for contributors.
5 *
6 * @author Wayne Stambaugh <[email protected]>
7 *
8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU General Public License
10 * as published by the Free Software Foundation; either version 2
11 * of the License, or (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License along
19 * with this program. If not, see <http://www.gnu.org/licenses/>.
20 */
21
22#include "sch_io_lib_cache.h"
23
24#include <common.h>
25#include <lib_symbol.h>
26#include <wx_filename.h>
27
28
29SCH_IO_LIB_CACHE::SCH_IO_LIB_CACHE( const wxString& aFullPathAndFileName ) :
30 m_modHash( 1 ),
31 m_fileName( aFullPathAndFileName ),
32 m_libFileName( aFullPathAndFileName ),
33 m_fileModTime( 0 ),
34 m_isWritable( true ),
35 m_isModified( false ),
36 m_hasParseError( false )
37{
39}
40
41
43{
44 // When the cache is destroyed, all of the alias objects on the heap should be deleted.
45 for( auto& symbol : m_symbols )
46 delete symbol.second;
47
48 m_symbols.clear();
49}
50
51
52void SCH_IO_LIB_CACHE::Save( const std::optional<bool>& aOpt )
53{
54 wxCHECK( false, /* void */ );
55}
56
57
59{
60 wxFileName fn( m_libFileName );
61
62 // If m_libFileName is a symlink follow it to the real source file
64 return fn;
65}
66
67
69{
70 wxFileName fn = GetRealFile();
71 wxString wildcard = fn.GetFullName();
72
73 // Update the writable flag while we have a wxFileName, in a network this is possibly quite dynamic anyway.
74 if( !fn.IsDir() )
75 {
76 m_isWritable = fn.IsFileWritable();
77 return fn.GetModificationTime().GetValue().GetValue();
78 }
79 else
80 {
81 m_isWritable = fn.IsDirWritable();
82 wildcard = wxS( "*." ) + wxString( FILEEXT::KiCadSymbolLibFileExtension );
83 return TimestampDir( fn.GetPath(), wildcard );
84 }
85}
86
87
88bool SCH_IO_LIB_CACHE::IsFile( const wxString& aFullPathAndFileName ) const
89{
90 return m_fileName == aFullPathAndFileName;
91}
92
93
95{
96 wxFileName fn = GetRealFile();
97
98 if( !fn.IsOk() )
99 return false;
100
101 if( !fn.IsDir() && fn.IsFileReadable() )
102 return fn.GetModificationTime().GetValue().GetValue() != m_fileModTime;
103
104 if( fn.IsDir() && fn.IsDirReadable() )
105 return TimestampDir( fn.GetPath(),
106 wxS( "*." ) + wxString( FILEEXT::KiCadSymbolLibFileExtension ) ) != m_fileModTime;
107
108 return false;
109}
110
111
113{
114 wxCHECK_MSG( aSymbol != nullptr, nullptr, "NULL pointer cannot be removed from library." );
115
116 LIB_SYMBOL* firstChild = nullptr;
117 LIB_SYMBOL_MAP::iterator it = m_symbols.find( aSymbol->GetName() );
118
119 if( it == m_symbols.end() )
120 return nullptr;
121
122 // If the entry pointer doesn't match the name it is mapped to in the library, we
123 // have done something terribly wrong.
124 wxCHECK_MSG( &*it->second == aSymbol, nullptr,
125 "Pointer mismatch while attempting to remove alias entry <" + aSymbol->GetName() +
126 "> from library cache <" + m_libFileName.GetName() + ">." );
127
128 // If the symbol is a root symbol used by other symbols find the first derived symbol that uses
129 // the root symbol and make it the new root.
130 if( aSymbol->IsRoot() )
131 {
132 for( const std::pair<const wxString, LIB_SYMBOL*>& entry : m_symbols )
133 {
134 if( entry.second->IsDerived()
135 && entry.second->GetParent().lock() == aSymbol->SharedPtr() )
136 {
137 firstChild = entry.second;
138 break;
139 }
140 }
141
142 if( firstChild )
143 {
144 for( SCH_ITEM& drawItem : aSymbol->GetDrawItems() )
145 {
146 if( drawItem.Type() == SCH_FIELD_T )
147 {
148 SCH_FIELD& field = static_cast<SCH_FIELD&>( drawItem );
149
150 if( firstChild->GetField( field.GetCanonicalName() ) )
151 continue;
152 }
153
154 SCH_ITEM* newItem = (SCH_ITEM*) drawItem.Clone();
155 drawItem.SetParent( firstChild );
156 firstChild->AddDrawItem( newItem );
157 }
158
159 // Reparent the remaining derived symbols.
160 for( const std::pair<const wxString, LIB_SYMBOL*>& entry : m_symbols )
161 {
162 if( entry.second->IsDerived()
163 && entry.second->GetParent().lock() == aSymbol->SharedPtr() )
164 {
165 entry.second->SetParent( firstChild );
166 }
167 }
168 }
169 }
170
171 m_symbols.erase( it );
172 delete aSymbol;
173 m_isModified = true;
175 return firstChild;
176}
177
178
180{
181 // aSymbol is cloned in SYMBOL_LIB::AddSymbol(). The cache takes ownership of aSymbol.
182 wxString name = aSymbol->GetName();
183 LIB_SYMBOL_MAP::iterator it = m_symbols.find( name );
184
185 if( it != m_symbols.end() )
186 {
187 removeSymbol( it->second );
188 }
189
190 m_symbols[ name ] = const_cast< LIB_SYMBOL* >( aSymbol );
191 m_isModified = true;
193}
194
195
197{
198 LIB_SYMBOL_MAP::iterator it = m_symbols.find( aName );
199
200 if( it != m_symbols.end() )
201 {
202 return it->second;
203 }
204
205 return nullptr;
206}
const char * name
virtual void SetParent(EDA_ITEM *aParent)
Definition eda_item.h:113
virtual EDA_ITEM * Clone() const
Create a duplicate of this item with linked list members set to NULL.
Definition eda_item.cpp:118
Define a library symbol object.
Definition lib_symbol.h:83
bool IsRoot() const override
For symbols derived from other symbols, IsRoot() indicates no derivation.
Definition lib_symbol.h:203
SCH_FIELD * GetField(const wxString &aFieldName)
Find a field within this symbol matching aFieldName; return nullptr if not found.
LIB_ITEMS_CONTAINER & GetDrawItems()
Return a reference to the draw item list.
Definition lib_symbol.h:699
wxString GetName() const override
Definition lib_symbol.h:146
std::shared_ptr< LIB_SYMBOL > SharedPtr() const
http://www.boost.org/doc/libs/1_55_0/libs/smart_ptr/sp_techniques.html#weak_without_shared.
Definition lib_symbol.h:93
void AddDrawItem(SCH_ITEM *aItem, bool aSort=true)
Add a new draw aItem to the draw object list and sort according to aSort.
wxString GetCanonicalName() const
Get a non-language-specific name for a field which can be used for storage, variable look-up,...
bool IsFile(const wxString &aFullPathAndFileName) const
virtual LIB_SYMBOL * GetSymbol(const wxString &aName)
virtual void AddSymbol(const LIB_SYMBOL *aSymbol)
SCH_LIB_TYPE m_libType
LIB_SYMBOL_MAP m_symbols
wxFileName GetRealFile() const
bool IsFileChanged() const
long long GetLibModificationTime()
virtual void Save(const std::optional< bool > &aOpt=std::nullopt)
Save the entire library to file m_libFileName;.
SCH_IO_LIB_CACHE(const wxString &aLibraryPath)
LIB_SYMBOL * removeSymbol(LIB_SYMBOL *aAlias)
Base class for any item which can be embedded within the SCHEMATIC container class,...
Definition sch_item.h:167
static void ResolvePossibleSymlinks(wxFileName &aFilename)
long long TimestampDir(const wxString &aDirPath, const wxString &aFilespec)
A copy of ConvertFileTimeToWx() because wxWidgets left it as a static function private to src/common/...
Definition common.cpp:814
The common library.
static const std::string KiCadSymbolLibFileExtension
@ SCH_FIELD_T
Definition typeinfo.h:154