##// END OF EJS Templates
added Qt4 compatibility and pre ARM_NONE_EABI libelf.
Jeandet Alexis -
r6:589c372f2986 default
parent child
Show More
@@ -1,150 +1,155
1 1 #include "binaryfilewidget.h"
2 2 #include "ui_binaryfilewidget.h"
3 3 #include "qtablewidgetintitem.h"
4 #include <QtWidgets/QTableWidget>
5 #include <QtWidgets/QFileDialog>
4 #if QT_VERSION >= 0x050000
5 #include <QtWidgets/QTableWidget>
6 #include <QtWidgets/QFileDialog>
7 #else
8 #include <QTableWidget>
9 #include <QFileDialog>
10 #endif
6 11 #include "srecfile.h"
7 12
8 13 binaryFileWidget::binaryFileWidget(QWidget *parent) :
9 14 abstractBinFileWidget(parent),
10 15 ui(new Ui::binaryFileWidget)
11 16 {
12 17 ui->setupUi(this);
13 18 connect(this->ui->fragmentList,SIGNAL(cellActivated(int,int)),this,SLOT(fragmentCellActivated(int,int)));
14 19 connect(this->ui->fragmentList,SIGNAL(cellChanged(int,int)),this,SLOT(fragmentCellChanged(int,int)));
15 20 exportToSREC_action = new QAction(tr("Export to SREC"),this);
16 21 exportToBIN_action = new QAction(tr("Export to Binary"),this);
17 22 this->ui->fragmentList->addAction(exportToBIN_action);
18 23 this->ui->fragmentList->addAction(exportToSREC_action);
19 24 connect(this->exportToBIN_action,SIGNAL(triggered()),this,SLOT(exportToBIN()));
20 25 connect(this->exportToSREC_action,SIGNAL(triggered()),this,SLOT(exportToSREC()));
21 26 }
22 27
23 28 binaryFileWidget::~binaryFileWidget()
24 29 {
25 30 delete ui;
26 31 }
27 32
28 33 void binaryFileWidget::setFile(abstractBinFile *file)
29 34 {
30 35 this->p_binfile = (binaryFile*)file;
31 36 if(p_binfile->isopened())
32 37 {
33 38 reloadFile();
34 39 }
35 40 }
36 41
37 42 void binaryFileWidget::reloadFile()
38 43 {
39 44 this->ui->fragmentList->clear();
40 45 this->ui->fragmentList->setRowCount(p_binfile->getFragmentsCount());
41 46 this->ui->fragmentList->setHorizontalHeaderLabels(QStringList()<<"File"<<"Size"<<"Address");
42 47 for(int i=0;i<p_binfile->getFragmentsCount();i++)
43 48 {
44 49 QTableWidgetItem *newItem = new QTableWidgetItem(p_binfile->getFragmentHeader(i));
45 50 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
46 51 this->ui->fragmentList->setItem(i, 0, newItem);
47 52
48 53 newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("%1").arg(p_binfile->getFragmentSize(i)),DecimalItem);
49 54 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
50 55 this->ui->fragmentList->setItem(i, 1, newItem);
51 56
52 57 newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("0x%1").arg(p_binfile->getFragmentAddress(i),8,16).replace(" ","0"),HexaDecimalItem);
53 58 // newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
54 59 this->ui->fragmentList->setItem(i, 2, newItem);
55 60
56 61 }
57 62 this->ui->fragmentList->resizeColumnsToContents();
58 63 }
59 64
60 65 void binaryFileWidget::fragmentCellActivated(int row, int column)
61 66 {
62 67 Q_UNUSED(column)
63 68 char* buff=NULL;
64 69 int index = this->ui->fragmentList->item(row,0)->text().toInt();
65 70 if(index!=-1)
66 71 {
67 72 this->p_binfile->getFragmentData(index,&buff);
68 73 this->ui->hexViewer->setData(QByteArray(buff,this->p_binfile->getFragmentSize(index)));
69 74 this->ui->hexViewer->setAddressOffset(this->p_binfile->getFragmentAddress(index));
70 75 }
71 76 }
72 77
73 78 void binaryFileWidget::fragmentCellChanged(int row, int column)
74 79 {
75 80 if(column==2)
76 81 {
77 82 QString newAddressStr = this->ui->fragmentList->item(row,column)->text();
78 83 int newAddress = 0;
79 84 newAddressStr.remove(" ");
80 85 if(newAddressStr.at(0)=='0' && newAddressStr.at(1)=='x')
81 86 {
82 87 newAddress = newAddressStr.remove("0x").toUInt(0,16);
83 88 }
84 89 else
85 90 {
86 91 newAddress = newAddressStr.toUInt();
87 92 }
88 93 this->p_binfile->getFragments().at(row)->address = newAddress;
89 94 }
90 95 }
91 96
92 97 void binaryFileWidget::exportToSREC()
93 98 {
94 99 QList<codeFragment *> SelectedFragmentsList=getSelectedFragments();
95 100 if(SelectedFragmentsList.count()>0)
96 101 {
97 102 QString fileName = QFileDialog::getSaveFileName(this, tr("Save File"),
98 103 NULL,
99 104 tr("SREC Files (*.srec)"));
100 105 if(!fileName.isEmpty())
101 106 {
102 107 srecFile::toSrec(SelectedFragmentsList,fileName);
103 108 }
104 109 }
105 110 }
106 111
107 112 void binaryFileWidget::exportToBIN()
108 113 {
109 114 QList<codeFragment *> SelectedFragmentsList=getSelectedFragments();
110 115 if(SelectedFragmentsList.count()>0)
111 116 {
112 117 QString fileName = QFileDialog::getSaveFileName(this, tr("Save File"),
113 118 NULL,
114 119 tr("Binary Files (*.bin)"));
115 120 if(!fileName.isEmpty())
116 121 {
117 122 binaryFile::toBinary(SelectedFragmentsList,fileName);
118 123 }
119 124 }
120 125 }
121 126
122 127 QStringList binaryFileWidget::getSelectedFilesNames()
123 128 {
124 129 QStringList SelectedFilesList;
125 130 QList<QTableWidgetItem*> items = this->ui->fragmentList->selectedItems();
126 131 for(int i=0;i<items.count();i++)
127 132 {
128 133 QString file = p_binfile->getFragmentHeader(items.at(i)->row());
129 134 if(!SelectedFilesList.contains(file))
130 135 {
131 136 SelectedFilesList.append(file);
132 137 }
133 138 }
134 139 return SelectedFilesList;
135 140 }
136 141
137 142 QList<codeFragment *> binaryFileWidget::getSelectedFragments()
138 143 {
139 144 QList<codeFragment *> SelectedFragmentsList;
140 145 QList<QTableWidgetItem*> items = this->ui->fragmentList->selectedItems();
141 146 for(int i=0;i<items.count();i++)
142 147 {
143 148 codeFragment * fragment = p_binfile->getFragment(items.at(i)->row());
144 149 if(!SelectedFragmentsList.contains(fragment))
145 150 {
146 151 SelectedFragmentsList.append(fragment);
147 152 }
148 153 }
149 154 return SelectedFragmentsList;
150 155 }
@@ -1,71 +1,74
1 1 /*------------------------------------------------------------------------------
2 2 -- This file is a part of the SocExplorer Software
3 3 -- Copyright (C) 2014, Plasma Physics Laboratory - CNRS
4 4 --
5 5 -- This program is free software; you can redistribute it and/or modify
6 6 -- it under the terms of the GNU General Public License as published by
7 7 -- the Free Software Foundation; either version 2 of the License, or
8 8 -- (at your option) any later version.
9 9 --
10 10 -- This program is distributed in the hope that it will be useful,
11 11 -- but WITHOUT ANY WARRANTY; without even the implied warranty of
12 12 -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 13 -- GNU General Public License for more details.
14 14 --
15 15 -- You should have received a copy of the GNU General Public License
16 16 -- along with this program; if not, write to the Free Software
17 17 -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 18 -------------------------------------------------------------------------------*/
19 19 /*-- Author : Alexis Jeandet
20 20 -- Mail : alexis.jeandet@member.fsf.org
21 21 ----------------------------------------------------------------------------*/
22 22 #ifndef ABSTRACTBINFILE_H
23 23 #define ABSTRACTBINFILE_H
24
25 #include <QtCore/QObject>
26 #include <QtWidgets/QWidget>
27
24 #if QT_VERSION >= 0x050000
25 #include <QtCore/QObject>
26 #include <QtWidgets/QWidget>
27 #else
28 #include <QObject>
29 #include <QWidget>
30 #endif
28 31 class codeFragment
29 32 {
30 33 public:
31 34 codeFragment();
32 35 codeFragment(char* data, quint64 size, quint64 address):data(data),size(size),address(address){}
33 36 ~codeFragment()
34 37 {
35 38 free(data);
36 39 }
37 40 QString header;
38 41 char* data;
39 42 quint64 size;
40 43 quint64 address;
41 44 };
42 45
43 46 class abstractBinFile : public QObject
44 47 {
45 48 Q_OBJECT
46 49 public:
47 50
48 51 virtual bool openFile(const QString& File)=0;
49 52 virtual bool isopened()=0;
50 53 virtual int closeFile()=0;
51 54 virtual QList<codeFragment*> getFragments()=0;
52 55 virtual bool toSrec(const QString& File)=0;
53 56 virtual bool toBinary(const QString& File)=0;
54 57 protected:
55 58 QString p_fileName;
56 59 };
57 60
58 61
59 62 class abstractBinFileWidget : public QWidget
60 63 {
61 64 Q_OBJECT
62 65
63 66 public:
64 67 abstractBinFileWidget(QWidget* parent = 0):QWidget(parent){}
65 68
66 69 public slots:
67 70 virtual void setFile(abstractBinFile* file)=0;
68 71 virtual void reloadFile()=0;
69 72 };
70 73
71 74 #endif // ABSTRACTBINFILE_H
@@ -1,1075 +1,1077
1 1 /*------------------------------------------------------------------------------
2 2 -- This file is a part of the SocExplorer Software
3 3 -- Copyright (C) 2014, Plasma Physics Laboratory - CNRS
4 4 --
5 5 -- This program is free software; you can redistribute it and/or modify
6 6 -- it under the terms of the GNU General Public License as published by
7 7 -- the Free Software Foundation; either version 2 of the License, or
8 8 -- (at your option) any later version.
9 9 --
10 10 -- This program is distributed in the hope that it will be useful,
11 11 -- but WITHOUT ANY WARRANTY; without even the implied warranty of
12 12 -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 13 -- GNU General Public License for more details.
14 14 --
15 15 -- You should have received a copy of the GNU General Public License
16 16 -- along with this program; if not, write to the Free Software
17 17 -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 18 -------------------------------------------------------------------------------*/
19 19 /*-- Author :
20 20 Alexis Jeandet
21 21 -- Mail :
22 22 alexis.jeandet@member.fsf.org
23 23 ----------------------------------------------------------------------------*/
24 24 #include "elffile.h"
25 25 #include "srecfile.h"
26 26 #include "binaryfile.h"
27 27 #include <stdint.h>
28 28
29 29 ElfFile::ElfFile()
30 30 :abstractBinFile()
31 31 {
32 32 this->opened = false;
33 33 this->type_elf = false;
34 34 this->elfFile = (int)NULL;
35 35 this->e = NULL;
36 36 }
37 37
38 38 ElfFile::ElfFile(const QString &File)
39 39 :abstractBinFile()
40 40 {
41 41 this->opened = false;
42 42 this->type_elf = false;
43 43 this->elfFile = (int)NULL;
44 44 this->e = NULL;
45 45 this->p_fileName = File;
46 46 openFile(File);
47 47 }
48 48
49 49 ElfFile::~ElfFile()
50 50 {
51 51 closeFile();
52 52 if(scn)free(scn);
53 53 if(data)free(data);
54 54 for(int i=0;i<this->sections.count();i++)
55 55 {
56 56 delete this->sections.at(i);
57 57 }
58 58 this->sections.clear();
59 59 for(int i=0;i<this->Segments.count();i++)
60 60 {
61 61 free(this->Segments.at(i));
62 62 }
63 63 this->Segments.clear();
64 64 for(int i=0;i<symbols.count();i++)
65 65 {
66 66 delete this->symbols.at(i);
67 67 }
68 68 this->symbols.clear();
69 69 }
70 70
71 71 bool ElfFile::openFile(const QString &File)
72 72 {
73 73 this->p_fileName = File;
74 74 this->closeFile();
75 75 if(elf_version(EV_CURRENT)==EV_NONE)return 0;
76 76 #ifdef _ELF_WINDOWS_
77 77 this->elfFile = open(File.toStdString().c_str(),O_RDONLY|O_BINARY ,0);
78 78 #else
79 79 this->elfFile = open(File.toStdString().c_str(),O_RDONLY ,0);
80 80 #endif
81 81 if(this->elfFile==(int)NULL)return 0;
82 82 this->e = elf_begin(this->elfFile,ELF_C_READ,NULL);
83 83 if(this->e==NULL)return 0;
84 84 this->ek = elf_kind(this->e);
85 85 gelf_getehdr (this->e, &this->ehdr );
86 86 elf_getshdrstrndx (this->e, &this->shstrndx);
87 87 this->updateSegments();
88 88 this->updateSections();
89 89 this->updateSymbols();
90 90 this->opened = true;
91 91 return 1;
92 92 }
93 93
94 94 bool ElfFile::isopened()
95 95 {
96 96 return this->opened;
97 97 }
98 98
99 99 int ElfFile::closeFile()
100 100 {
101 101 if(this->elfFile!=(int)NULL)
102 102 {
103 103 if(this->e!=NULL)
104 104 {
105 105 elf_end(this->e);
106 106 this->e = NULL;
107 107 }
108 108 close(this->elfFile);
109 109 this->elfFile = (int)NULL;
110 110 }
111 111 this->opened = false;
112 112 return 0;
113 113 }
114 114
115 115
116 116 QList<codeFragment*> ElfFile::getFragments(QStringList fragmentList)
117 117 {
118 118 QList<codeFragment*> fragments;
119 119 if (isopened())
120 120 {
121 121 for(int i =0;i<fragmentList.count();i++)
122 122 {
123 123 fragments.append(getFragment(fragmentList.at(i)));
124 124 }
125 125 }
126 126 return fragments;
127 127 }
128 128
129 129 QList<codeFragment*> ElfFile::getFragments()
130 130 {
131 131 return getFragments(QStringList()<<".data"<<".text");
132 132 }
133 133
134 134 codeFragment *ElfFile::getFragment(const QString &name)
135 135 {
136 136 codeFragment* fragment= new codeFragment();
137 137 for(int i=0;i<getSectionCount();i++)
138 138 {
139 139 if(getSectionName(i) == name)
140 140 {
141 141 fragment->data =NULL;
142 142 fragment->size = getSectionDatasz(i);
143 143 fragment->address = getSectionPaddr(i);
144 144 getSectionData(i,&fragment->data);
145 145 }
146 146 }
147 147 return fragment;
148 148 }
149 149
150 150
151 151
152 152
153 153
154 154
155 155
156 156 QString elfresolveMachine(Elf64_Half e_machine)
157 157 {
158 158 QString machineName;
159 159 //Update from with bash script don't write it by yourself!
160 160 switch(e_machine)
161 161 {
162 162 case EM_NONE:
163 163 machineName = " No machine ";
164 164 break;
165 165 case EM_M32:
166 166 machineName = " AT&T WE 32100 ";
167 167 break;
168 168 case EM_SPARC:
169 169 machineName = " SUN SPARC ";
170 170 break;
171 171 case EM_386:
172 172 machineName = " Intel 80386 ";
173 173 break;
174 174 case EM_68K:
175 175 machineName = " Motorola m68k family ";
176 176 break;
177 177 case EM_88K:
178 178 machineName = " Motorola m88k family ";
179 179 break;
180 180 case EM_860:
181 181 machineName = " Intel 80860 ";
182 182 break;
183 183 case EM_MIPS:
184 184 machineName = " MIPS R3000 big-endian ";
185 185 break;
186 186 case EM_S370:
187 187 machineName = " IBM System/370 ";
188 188 break;
189 189 case EM_MIPS_RS3_LE:
190 190 machineName = " MIPS R3000 little-endian ";
191 191 break;
192 192 case EM_PARISC:
193 193 machineName = " HPPA ";
194 194 break;
195 195 case EM_VPP500:
196 196 machineName = " Fujitsu VPP500 ";
197 197 break;
198 198 case EM_SPARC32PLUS:
199 199 machineName = " Sun's \"v8plus\" ";
200 200 break;
201 201 case EM_960:
202 202 machineName = " Intel 80960 ";
203 203 break;
204 204 case EM_PPC:
205 205 machineName = " PowerPC ";
206 206 break;
207 207 case EM_PPC64:
208 208 machineName = " PowerPC 64-bit ";
209 209 break;
210 210 case EM_S390:
211 211 machineName = " IBM S390 ";
212 212 break;
213 213 case EM_V800:
214 214 machineName = " NEC V800 series ";
215 215 break;
216 216 case EM_FR20:
217 217 machineName = " Fujitsu FR20 ";
218 218 break;
219 219 case EM_RH32:
220 220 machineName = " TRW RH-32 ";
221 221 break;
222 222 case EM_RCE:
223 223 machineName = " Motorola RCE ";
224 224 break;
225 225 case EM_ARM:
226 226 machineName = " ARM ";
227 227 break;
228 228 case EM_FAKE_ALPHA:
229 229 machineName = " Digital Alpha ";
230 230 break;
231 231 case EM_SH:
232 232 machineName = " Hitachi SH ";
233 233 break;
234 234 case EM_SPARCV9:
235 235 machineName = " SPARC v9 64-bit ";
236 236 break;
237 237 case EM_TRICORE:
238 238 machineName = " Siemens Tricore ";
239 239 break;
240 240 case EM_ARC:
241 241 machineName = " Argonaut RISC Core ";
242 242 break;
243 243 case EM_H8_300:
244 244 machineName = " Hitachi H8/300 ";
245 245 break;
246 246 case EM_H8_300H:
247 247 machineName = " Hitachi H8/300H ";
248 248 break;
249 249 case EM_H8S:
250 250 machineName = " Hitachi H8S ";
251 251 break;
252 252 case EM_H8_500:
253 253 machineName = " Hitachi H8/500 ";
254 254 break;
255 255 case EM_IA_64:
256 256 machineName = " Intel Merced ";
257 257 break;
258 258 case EM_MIPS_X:
259 259 machineName = " Stanford MIPS-X ";
260 260 break;
261 261 case EM_COLDFIRE:
262 262 machineName = " Motorola Coldfire ";
263 263 break;
264 264 case EM_68HC12:
265 265 machineName = " Motorola M68HC12 ";
266 266 break;
267 267 case EM_MMA:
268 268 machineName = " Fujitsu MMA Multimedia Accelerator";
269 269 break;
270 270 case EM_PCP:
271 271 machineName = " Siemens PCP ";
272 272 break;
273 273 case EM_NCPU:
274 274 machineName = " Sony nCPU embeeded RISC ";
275 275 break;
276 276 case EM_NDR1:
277 277 machineName = " Denso NDR1 microprocessor ";
278 278 break;
279 279 case EM_STARCORE:
280 280 machineName = " Motorola Start*Core processor ";
281 281 break;
282 282 case EM_ME16:
283 283 machineName = " Toyota ME16 processor ";
284 284 break;
285 285 case EM_ST100:
286 286 machineName = " STMicroelectronic ST100 processor ";
287 287 break;
288 288 case EM_TINYJ:
289 289 machineName = " Advanced Logic Corp. Tinyj emb.fam";
290 290 break;
291 291 case EM_X86_64:
292 292 machineName = " AMD x86-64 architecture ";
293 293 break;
294 294 case EM_PDSP:
295 295 machineName = " Sony DSP Processor ";
296 296 break;
297 297 case EM_FX66:
298 298 machineName = " Siemens FX66 microcontroller ";
299 299 break;
300 300 case EM_ST9PLUS:
301 301 machineName = " STMicroelectronics ST9+ 8/16 mc ";
302 302 break;
303 303 case EM_ST7:
304 304 machineName = " STmicroelectronics ST7 8 bit mc ";
305 305 break;
306 306 case EM_68HC16:
307 307 machineName = " Motorola MC68HC16 microcontroller ";
308 308 break;
309 309 case EM_68HC11:
310 310 machineName = " Motorola MC68HC11 microcontroller ";
311 311 break;
312 312 case EM_68HC08:
313 313 machineName = " Motorola MC68HC08 microcontroller ";
314 314 break;
315 315 case EM_68HC05:
316 316 machineName = " Motorola MC68HC05 microcontroller ";
317 317 break;
318 318 case EM_SVX:
319 319 machineName = " Silicon Graphics SVx ";
320 320 break;
321 321 case EM_ST19:
322 322 machineName = " STMicroelectronics ST19 8 bit mc ";
323 323 break;
324 324 case EM_VAX:
325 325 machineName = " Digital VAX ";
326 326 break;
327 327 case EM_CRIS:
328 328 machineName = " Axis Communications 32-bit embedded processor ";
329 329 break;
330 330 case EM_JAVELIN:
331 331 machineName = " Infineon Technologies 32-bit embedded processor ";
332 332 break;
333 333 case EM_FIREPATH:
334 334 machineName = " Element 14 64-bit DSP Processor ";
335 335 break;
336 336 case EM_ZSP:
337 337 machineName = " LSI Logic 16-bit DSP Processor ";
338 338 break;
339 339 case EM_MMIX:
340 340 machineName = " Donald Knuth's educational 64-bit processor ";
341 341 break;
342 342 case EM_HUANY:
343 343 machineName = " Harvard University machine-independent object files ";
344 344 break;
345 345 case EM_PRISM:
346 346 machineName = " SiTera Prism ";
347 347 break;
348 348 case EM_AVR:
349 349 machineName = " Atmel AVR 8-bit microcontroller ";
350 350 break;
351 351 case EM_FR30:
352 352 machineName = " Fujitsu FR30 ";
353 353 break;
354 354 case EM_D10V:
355 355 machineName = " Mitsubishi D10V ";
356 356 break;
357 357 case EM_D30V:
358 358 machineName = " Mitsubishi D30V ";
359 359 break;
360 360 case EM_V850:
361 361 machineName = " NEC v850 ";
362 362 break;
363 363 case EM_M32R:
364 364 machineName = " Mitsubishi M32R ";
365 365 break;
366 366 case EM_MN10300:
367 367 machineName = " Matsushita MN10300 ";
368 368 break;
369 369 case EM_MN10200:
370 370 machineName = " Matsushita MN10200 ";
371 371 break;
372 372 case EM_PJ:
373 373 machineName = " picoJava ";
374 374 break;
375 375 case EM_OPENRISC:
376 376 machineName = " OpenRISC 32-bit embedded processor ";
377 377 break;
378 378 case EM_ARC_A5:
379 379 machineName = " ARC Cores Tangent-A5 ";
380 380 break;
381 381 case EM_XTENSA:
382 382 machineName = " Tensilica Xtensa Architecture ";
383 383 break;
384 384 case EM_AARCH64:
385 385 machineName = " ARM AARCH64 ";
386 386 break;
387 387 case EM_TILEPRO:
388 388 machineName = " Tilera TILEPro ";
389 389 break;
390 390 case EM_MICROBLAZE:
391 391 machineName = " Xilinx MicroBlaze ";
392 392 break;
393 393 case EM_TILEGX:
394 394 machineName = " Tilera TILE-Gx ";
395 395 break;
396 396 case EM_NUM:
397 397 machineName = "";
398 398 break;
399 399 default:
400 400 machineName ="Unknow Machine";
401 401 break;
402 402 }
403 403 return machineName;
404 404 }
405 405
406 406
407 407
408 408
409 409 QString ElfFile::getClass()
410 410 {
411 411 if(this->e!=NULL)
412 412 {
413 413 int eclass = gelf_getclass(this->e);
414 414 if(eclass==ELFCLASS32)return "ELF32";
415 415 if(eclass==ELFCLASS64)return "ELF64";
416 416 }
417 417 return "none";
418 418 }
419 419
420 420
421 421 bool ElfFile::iself()
422 422 {
423 423 return (this->getType()!="Unknow");
424 424 }
425 425
426 426 QString ElfFile::getArchitecture()
427 427 {
428 428 if(this->e!=NULL)
429 429 {
430 430 return elfresolveMachine(this->ehdr.e_machine);
431 431 }
432 432 return "";
433 433 }
434 434
435 435
436 436 QString ElfFile::getType()
437 437 {
438 438 QString kind("");
439 439 if(this->e!=NULL)
440 440 {
441 441 switch(this->ek)
442 442 {
443 443 case ELF_K_AR:
444 444 kind = "Archive";
445 445 break;
446 446 case ELF_K_ELF:
447 447 kind = "Elf";
448 448 break;
449 449 case ELF_K_COFF:
450 450 kind = "COFF";
451 451 break;
452 452 case ELF_K_NUM:
453 453 kind = "NUM";
454 454 break;
455 455 case ELF_K_NONE:
456 456 kind = "Data";
457 457 break;
458 458 default:
459 459 kind = "Unknow";
460 460 break;
461 461 }
462 462 }
463 463 return kind;
464 464 }
465 465
466 466 QString ElfFile::getEndianness()
467 467 {
468 468 if(this->e!=NULL)
469 469 {
470 470 if(this->ehdr.e_ident[EI_DATA]==ELFDATA2LSB)return "2's complement, little endian";
471 471 if(this->ehdr.e_ident[EI_DATA]==ELFDATA2MSB)return "2's complement, big endian";
472 472 }
473 473 return "none";
474 474 }
475 475
476 476 QString ElfFile::getABI()
477 477 {
478 478 if(this->e!=NULL)
479 479 {
480 480 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_NONE)return "UNIX System V ABI";
481 481 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_SYSV)return "Alias";
482 482 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_HPUX)return "HP-UX";
483 483 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_NETBSD)return "NetBSD";
484 484 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_LINUX)return "Object uses GNU ELF extensions";
485 485 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_SOLARIS)return "Sun Solaris";
486 486 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_AIX)return "IBM AIX";
487 487 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_IRIX)return "SGI Irix";
488 488 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_FREEBSD)return "FreeBSD";
489 489 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_TRU64)return "Compaq TRU64 UNIX";
490 490 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_MODESTO)return " Novell Modesto";
491 491 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_OPENBSD)return "OpenBSD";
492 #ifdef ELFOSABI_ARM_AEABI
492 493 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_ARM_AEABI)return "ARM EABI";
494 #endif
493 495 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_ARM)return "ARM";
494 496 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_STANDALONE)return "Standalone (embedded) application";
495 497 }
496 498 return "none";
497 499 }
498 500
499 501
500 502 qint64 ElfFile::getVersion()
501 503 {
502 504 if(this->e!=NULL)
503 505 {
504 506 return this->ehdr.e_version;
505 507 }
506 508 return -1;
507 509 }
508 510
509 511 qint64 ElfFile::getEntryPointAddress()
510 512 {
511 513 if(this->e!=NULL)
512 514 {
513 515 return this->ehdr.e_entry;
514 516 }
515 517 return -1;
516 518 }
517 519
518 520
519 521 int ElfFile::getSectionCount()
520 522 {
521 523 return (int)this->SectionCount;
522 524 }
523 525
524 526 int ElfFile::getSymbolCount()
525 527 {
526 528 return (int)this->SymbolCount;
527 529 }
528 530
529 531
530 532 int ElfFile::getSegmentCount()
531 533 {
532 534 return (int)this->SegmentCount;
533 535 }
534 536
535 537
536 538 QString ElfFile::getSegmentType(int index)
537 539 {
538 540 QString type("");
539 541 if(this->e!=NULL)
540 542 {
541 543 if(index < this->Segments.count())
542 544 {
543 545 switch(this->Segments.at(index)->p_type)
544 546 {
545 547 case PT_NULL:
546 548 type = "Program header table entry unused";
547 549 break;
548 550 case PT_LOAD:
549 551 type = "Loadable program segment";
550 552 break;
551 553 case PT_DYNAMIC :
552 554 type = "Dynamic linking information";
553 555 break;
554 556 case PT_INTERP:
555 557 type ="Program interpreter";
556 558 break;
557 559 case PT_NOTE:
558 560 type = "Auxiliary information";
559 561 break;
560 562 case PT_SHLIB:
561 563 type = "Reserved";
562 564 break;
563 565 case PT_PHDR:
564 566 type = "Entry for header table itself";
565 567 break;
566 568 case PT_TLS:
567 569 type = "Thread-local storage segment";
568 570 break;
569 571 case PT_NUM:
570 572 type = "Number of defined types";
571 573 break;
572 574 case PT_LOOS:
573 575 type = "Start of OS-specific";
574 576 break;
575 577 case PT_SUNWSTACK:
576 578 type = "Stack segment";
577 579 break;
578 580 case PT_LOPROC:
579 581 type = "Start of processor-specific";
580 582 break;
581 583 case PT_HIPROC:
582 584 type = "End of processor-specific";
583 585 break;
584 586 default:
585 587 type = "Unknow Section Type";
586 588 break;
587 589 }
588 590 }
589 591 }
590 592
591 593 return type;
592 594 }
593 595
594 596
595 597 qint64 ElfFile::getSegmentOffset(int index)
596 598 {
597 599 qint64 Offset = -1;
598 600 if(this->e!=NULL)
599 601 {
600 602 if(index < this->Segments.count())
601 603 {
602 604 Offset = (qint64)this->Segments.at(index)->p_offset;
603 605 }
604 606 }
605 607 return Offset;
606 608 }
607 609
608 610
609 611 qint64 ElfFile::getSegmentVaddr(int index)
610 612 {
611 613 int64_t Vaddr = 0;
612 614 if(this->e!=NULL)
613 615 {
614 616 if(index < this->Segments.count())
615 617 {
616 618 Vaddr = (int64_t)this->Segments.at(index)->p_vaddr;
617 619 }
618 620 }
619 621 return Vaddr;
620 622 }
621 623
622 624
623 625 qint64 ElfFile::getSegmentPaddr(int index)
624 626 {
625 627 int64_t Paddr=0;
626 628 if(this->e!=NULL)
627 629 {
628 630 if(index < this->Segments.count())
629 631 {
630 632 Paddr = (int64_t)this->Segments.at(index)->p_paddr;
631 633 }
632 634 }
633 635 return Paddr;
634 636 }
635 637
636 638 qint64 ElfFile::getSectionPaddr(int index)
637 639 {
638 640 int64_t Paddr=0;
639 641 if(this->e!=NULL)
640 642 {
641 643 if(index < this->sections.count())
642 644 {
643 645 Paddr = (int64_t)this->sections.at(index)->section_header->sh_addr;
644 646 }
645 647 }
646 648 return Paddr;
647 649 }
648 650
649 651
650 652 qint64 ElfFile::getSegmentFilesz(int index)
651 653 {
652 654 int64_t FileSz=0;
653 655 if(this->e!=NULL)
654 656 {
655 657 if(index < this->Segments.count())
656 658 {
657 659 FileSz = (int64_t)this->Segments.at(index)->p_filesz;
658 660 }
659 661 }
660 662 return FileSz;
661 663 }
662 664
663 665 qint64 ElfFile::getSectionDatasz(int index)
664 666 {
665 667 int64_t DataSz=0;
666 668 if(this->e!=NULL)
667 669 {
668 670 if(index < this->sections.count())
669 671 {
670 672 if(this->sections.at(index)->section_header->sh_type==SHT_NOBITS)
671 673 {
672 674 DataSz=0;
673 675 }
674 676 else
675 677 {
676 678 DataSz = (int64_t)this->sections.at(index)->data->d_size;
677 679 }
678 680 }
679 681 }
680 682 return DataSz;
681 683 }
682 684
683 685 bool ElfFile::getSectionData(int index, char **buffer)
684 686 {
685 687 if(this->e!=NULL)
686 688 {
687 689 if(index < this->sections.count())
688 690 {
689 691 *buffer = (char *)malloc(this->sections.at(index)->data->d_size);
690 692 memcpy(*buffer,this->sections.at(index)->data->d_buf,this->sections.at(index)->data->d_size);
691 693 return true;
692 694 }
693 695 }
694 696 return false;
695 697 }
696 698
697 699
698 700 qint64 ElfFile::getSegmentMemsz(int index)
699 701 {
700 702 int64_t MemSz=0;
701 703 if(this->e!=NULL)
702 704 {
703 705 if(index < this->Segments.count())
704 706 {
705 707 MemSz = (int64_t)this->Segments.at(index)->p_memsz;
706 708 }
707 709 }
708 710 return MemSz;
709 711 }
710 712
711 713 qint64 ElfFile::getSectionMemsz(int index)
712 714 {
713 715 int64_t MemSz=0;
714 716 if(this->e!=NULL)
715 717 {
716 718 if(index < this->sections.count())
717 719 {
718 720 MemSz = (int64_t)this->sections.at(index)->section_header->sh_size;
719 721 }
720 722 }
721 723 return MemSz;
722 724 }
723 725
724 726
725 727 QString ElfFile::getSegmentFlags(int index)
726 728 {
727 729 QString flags("");
728 730 if(this->e!=NULL)
729 731 {
730 732 if(index < this->Segments.count())
731 733 {
732 734 if((this->Segments.at(index)->p_flags&PF_X) == PF_X)flags+="x";
733 735 if((this->Segments.at(index)->p_flags&PF_W) == PF_W)flags+="w";
734 736 if((this->Segments.at(index)->p_flags&PF_R) == PF_R)flags+="r";
735 737 if((this->Segments.at(index)->p_flags&PF_MASKOS) == PF_MASKOS)flags+=" OS-specific";
736 738 if((this->Segments.at(index)->p_flags&PF_MASKPROC) == PF_MASKPROC)flags+=" Processor-specific";
737 739 }
738 740 }
739 741 return flags;
740 742 }
741 743
742 744
743 745 QString ElfFile::getSectionName(int index)
744 746 {
745 747 if((index<sections.count()) && (index>=0))
746 748 {
747 749 char* nameChr = elf_strptr(this->e , this->shstrndx , this->sections.at(index)->section_header->sh_name);
748 750 return QString(nameChr);
749 751 }
750 752 return "";
751 753 }
752 754
753 755
754 756 void ElfFile::updateSections()
755 757 {
756 758 for(int i=0;i<this->sections.count();i++)
757 759 {
758 760 delete this->sections.at(i);
759 761 }
760 762 this->sections.clear();
761 763 this->scn = elf_nextscn (this->e , NULL );
762 764 this->SectionCount = 0;
763 765 while( this->scn != NULL )
764 766 {
765 767 GElf_Shdr* shdr = (GElf_Shdr*)malloc(sizeof(GElf_Shdr));
766 768 gelf_getshdr ( this->scn , shdr );
767 769 Elf_Data* data = elf_getdata(this->scn, NULL);
768 770 this->sections.append(new Elf_Section(data,shdr));
769 771 this->SectionCount+=1;
770 772 this->scn = elf_nextscn(e , scn);
771 773 }
772 774 }
773 775
774 776
775 777 void ElfFile::updateSegments()
776 778 {
777 779 elf_getphdrnum (this->e , &this->SegmentCount);
778 780 for(int i=0;i<this->Segments.count();i++)
779 781 {
780 782 free(this->Segments.at(i));
781 783 }
782 784 this->Segments.clear();
783 785 for(int i=0;i<(int)this->SegmentCount;i++)
784 786 {
785 787 GElf_Phdr* header=(GElf_Phdr*)malloc(sizeof(GElf_Phdr));
786 788 gelf_getphdr (this->e , i , header );
787 789 this->Segments.append(header);
788 790 }
789 791 }
790 792
791 793 void ElfFile::updateSymbols()
792 794 {
793 795 for(int i=0;i<symbols.count();i++)
794 796 {
795 797 delete this->symbols.at(i);
796 798 }
797 799 this->symbols.clear();
798 800 updateSections(); //Useless in most case but safer to do it
799 801 for(int i=0;i<(int)SectionCount;i++)
800 802 {
801 803 //First find Symbol table
802 804 if(this->getSectionName(i)==".symtab")
803 805 {
804 806 Elf_Section* sec = sections.at(i);
805 807 this->SymbolCount = sec->section_header->sh_size / sec->section_header->sh_entsize;
806 808 //Then list all symbols
807 809 for(int j=0;j<(int)this->SymbolCount;j++)
808 810 {
809 811 GElf_Sym* esym = (GElf_Sym*)malloc(sizeof(GElf_Sym));
810 812 gelf_getsym(sec->data, j, esym);
811 813 QString name = elf_strptr(this->e,sec->section_header->sh_link,esym->st_name);
812 814 Elf_Symbol* sym = new Elf_Symbol(name,esym);
813 815 symbols.append(sym);
814 816 }
815 817 }
816 818 }
817 819
818 820 }
819 821
820 822
821 823
822 824 QString ElfFile::getSectionType(int index)
823 825 {
824 826 QString type("");
825 827 if(this->e!=NULL)
826 828 {
827 829 if(index < this->sections.count())
828 830 {
829 831 switch(this->sections.at(index)->section_header->sh_type)
830 832 {
831 833 case SHT_NULL : type = "Section header table entry unused"; break;
832 834 case SHT_PROGBITS : type = "Program data"; break;
833 835 case SHT_SYMTAB : type = "Symbol table"; break;
834 836 case SHT_STRTAB : type = "String table"; break;
835 837 case SHT_RELA : type = "Relocation entries with addends"; break;
836 838 case SHT_HASH : type = "Symbol hash table"; break;
837 839 case SHT_DYNAMIC : type = "Dynamic linking information"; break;
838 840 case SHT_NOTE : type = "Notes"; break;
839 841 case SHT_NOBITS :type = "Program space with no data (bss)"; break;
840 842 case SHT_REL :type = "Relocation entries, no addends"; break;
841 843 case SHT_SHLIB : type = "Reserved"; break;
842 844 case SHT_DYNSYM : type = "Dynamic linker symbol table"; break;
843 845 case SHT_INIT_ARRAY : type = "Array of constructors"; break;
844 846 case SHT_FINI_ARRAY : type = "Array of destructors"; break;
845 847 case SHT_PREINIT_ARRAY : type = "Array of pre-constructors"; break;
846 848 case SHT_GROUP : type = "Section group"; break;
847 849 case SHT_SYMTAB_SHNDX : type = "Extended section indeces"; break;
848 850 case SHT_NUM : type = "Number of defined types. "; break;
849 851 case SHT_LOOS : type = "Start OS-specific. "; break;
850 852 case SHT_LOSUNW : type = "Sun-specific low bound. "; break;
851 853 case SHT_SUNW_COMDAT : type = " "; break;
852 854 case SHT_SUNW_syminfo : type = " "; break;
853 855 case SHT_GNU_verdef : type = "Version definition section. "; break;
854 856 case SHT_GNU_verneed : type = "Version needs section. "; break;
855 857 case SHT_GNU_versym : type = "Version symbol table. "; break;
856 858 case SHT_LOPROC : type = "Start of processor-specific"; break;
857 859 case SHT_HIPROC : type = "End of processor-specific"; break;
858 860 case SHT_HIUSER : type = "End of application-specific"; break;
859 861 }
860 862 }
861 863 }
862 864 return type;
863 865 }
864 866
865 867 int ElfFile::getSectionIndex(QString name)
866 868 {
867 869 if(this->e!=NULL)
868 870 {
869 871 for(int i=0;i<sections.count();i++)
870 872 {
871 873 if(getSectionName(i)==name)
872 874 return i;
873 875 }
874 876 }
875 877 return -1;
876 878 }
877 879
878 880 bool ElfFile::sectionIsNobits(int index)
879 881 {
880 882 if(this->e!=NULL)
881 883 {
882 884 if(index < this->sections.count())
883 885 {
884 886 return this->sections.at(index)->section_header->sh_type== SHT_NOBITS;
885 887 }
886 888 }
887 889 return false;
888 890 }
889 891
890 892 QString ElfFile::getSymbolName(int index)
891 893 {
892 894 if(this->e!=NULL)
893 895 {
894 896 if(index < this->symbols.count())
895 897 {
896 898 return symbols.at(index)->name;
897 899 }
898 900 }
899 901 return "";
900 902 }
901 903
902 904 QString ElfFile::getSymbolType(int index)
903 905 {
904 906 if(this->e!=NULL)
905 907 {
906 908 if(index < this->symbols.count())
907 909 {
908 910 int type = GELF_ST_TYPE(symbols.at(index)->sym->st_info);
909 911 switch(type)
910 912 {
911 913 case STT_NOTYPE:
912 914 return "No Type";
913 915 break;
914 916 case STT_OBJECT:
915 917 return "Object";
916 918 break;
917 919 case STT_FUNC:
918 920 return "Function";
919 921 break;
920 922 case STT_SECTION:
921 923 return "Section";
922 924 break;
923 925 case STT_FILE:
924 926 return "File";
925 927 break;
926 928 case STT_COMMON:
927 929 return "Common data object";
928 930 break;
929 931 case STT_TLS:
930 932 return "Thread-local data object";
931 933 break;
932 934 case STT_NUM:
933 935 return "Number of defined types";
934 936 break;
935 937 case STT_LOOS:
936 938 return "Start of OS-specific";
937 939 break;
938 940 case STT_HIOS:
939 941 return "End of OS-specific";
940 942 break;
941 943 case STT_LOPROC:
942 944 return "Start of processor-specific";
943 945 break;
944 946 case STT_HIPROC:
945 947 return "End of processor-specific";
946 948 break;
947 949 default:
948 950 return "none";
949 951 break;
950 952 }
951 953 }
952 954 }
953 955 return "none";
954 956 }
955 957
956 958 quint64 ElfFile::getSymbolSize(int index)
957 959 {
958 960 if(this->e!=NULL)
959 961 {
960 962 if((index < this->symbols.count()) && (index>=0))
961 963 {
962 964 return symbols.at(index)->sym->st_size;
963 965 }
964 966 }
965 967 return 0;
966 968 }
967 969
968 970 QString ElfFile::getSymbolSectionName(int index)
969 971 {
970 972 if(this->e!=NULL)
971 973 {
972 974 if((index < this->symbols.count()) && (index>=0))
973 975 {
974 976 return getSectionName(symbols.at(index)->sym->st_shndx-1);
975 977 }
976 978 }
977 979 return "none";
978 980 }
979 981
980 982 int ElfFile::getSymbolSectionIndex(int index)
981 983 {
982 984 if(this->e!=NULL)
983 985 {
984 986 if((index < this->symbols.count()) && (index>=0))
985 987 {
986 988 return symbols.at(index)->sym->st_shndx;
987 989 }
988 990 }
989 991 return 0;
990 992 }
991 993
992 994 quint64 ElfFile::getSymbolAddress(int index)
993 995 {
994 996 if(this->e!=NULL)
995 997 {
996 998 if((index < this->symbols.count()) && (index>=0))
997 999 {
998 1000 return symbols.at(index)->sym->st_value;
999 1001 }
1000 1002 }
1001 1003 return 0;
1002 1004 }
1003 1005
1004 1006 QString ElfFile::getSymbolLinkType(int index)
1005 1007 {
1006 1008 if(this->e!=NULL)
1007 1009 {
1008 1010 if(index < this->symbols.count())
1009 1011 {
1010 1012 int btype = GELF_ST_BIND(symbols.at(index)->sym->st_info);
1011 1013 switch(btype)
1012 1014 {
1013 1015 case STB_LOCAL:
1014 1016 return "Local";
1015 1017 break;
1016 1018 case STB_GLOBAL:
1017 1019 return "Global";
1018 1020 break;
1019 1021 case STB_WEAK:
1020 1022 return "Weak";
1021 1023 break;
1022 1024 case STB_NUM:
1023 1025 return "Number of defined types";
1024 1026 break;
1025 1027 case STB_LOOS:
1026 1028 return "Start of OS-specific";
1027 1029 break;
1028 1030 case STB_HIOS:
1029 1031 return "End of OS-specific";
1030 1032 break;
1031 1033 case STB_LOPROC:
1032 1034 return "Start of processor-specific";
1033 1035 break;
1034 1036 case STB_HIPROC:
1035 1037 return "End of processor-specific";
1036 1038 break;
1037 1039 default:
1038 1040 return "none";
1039 1041 break;
1040 1042 }
1041 1043 }
1042 1044 }
1043 1045 return "none";
1044 1046 }
1045 1047
1046 1048 bool ElfFile::isElf(const QString &File)
1047 1049 {
1048 1050 int file =0;
1049 1051 #ifdef _ELF_WINDOWS_
1050 1052 file = open(File.toStdString().c_str(),O_RDONLY|O_BINARY ,0);
1051 1053 #else
1052 1054 file = open(File.toStdString().c_str(),O_RDONLY ,0);
1053 1055 #endif
1054 1056 char Magic[4];
1055 1057 if(file!=-1)
1056 1058 {
1057 1059 size_t res = read(file,Magic,4);
1058 1060 close(file);
1059 1061 if((res==4) && (Magic[0]==0x7f) && (Magic[1]==0x45) && (Magic[2]==0x4c) && (Magic[3]==0x46))
1060 1062 {
1061 1063 return true;
1062 1064 }
1063 1065 }
1064 1066 return false;
1065 1067 }
1066 1068
1067 1069 bool ElfFile::toSrec(const QString &File)
1068 1070 {
1069 1071 return srecFile::toSrec(this->getFragments(),File);
1070 1072 }
1071 1073
1072 1074 bool ElfFile::toBinary(const QString &File)
1073 1075 {
1074 1076 return binaryFile::toBinary(getFragments(),File);
1075 1077 }
@@ -1,354 +1,359
1 1 /*------------------------------------------------------------------------------
2 2 -- This file is a part of the SocExplorer Software
3 3 -- Copyright (C) 2014, Plasma Physics Laboratory - CNRS
4 4 --
5 5 -- This program is free software; you can redistribute it and/or modify
6 6 -- it under the terms of the GNU General Public License as published by
7 7 -- the Free Software Foundation; either version 2 of the License, or
8 8 -- (at your option) any later version.
9 9 --
10 10 -- This program is distributed in the hope that it will be useful,
11 11 -- but WITHOUT ANY WARRANTY; without even the implied warranty of
12 12 -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 13 -- GNU General Public License for more details.
14 14 --
15 15 -- You should have received a copy of the GNU General Public License
16 16 -- along with this program; if not, write to the Free Software
17 17 -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 18 -------------------------------------------------------------------------------*/
19 19 /*-- Author : Alexis Jeandet
20 20 -- Mail : alexis.jeandet@member.fsf.org
21 21 ----------------------------------------------------------------------------*/
22 22 #include "elffilewidget.h"
23 23 #include "ui_elffilewidget.h"
24 #include <QtWidgets/QTableWidgetItem>
25 #include <QtWidgets/QFileDialog>
24 #if QT_VERSION >= 0x050000
25 #include <QtWidgets/QTableWidgetItem>
26 #include <QtWidgets/QFileDialog>
27 #else
28 #include <QTableWidgetItem>
29 #include <QFileDialog>
30 #endif
26 31 #include "qhexedit.h"
27 32 #include "qtablewidgetintitem.h"
28 33 #include "../srec/srecfile.h"
29 34 #include "../BinFile/binaryfile.h"
30 35
31 36 elfFileWidget::elfFileWidget(QWidget *parent) :
32 37 abstractBinFileWidget(parent),
33 38 ui(new Ui::elfFileWidget)
34 39 {
35 40 ui->setupUi(this);
36 41 exportToSREC_action = new QAction(tr("Export to SREC"),this);
37 42 exportToBIN_action = new QAction(tr("Export to Binary"),this);
38 43 viewSymbolInHexViewer_action = new QAction(tr("View in Hexviewer"),this);
39 44 connect(this->ui->sectionsList,SIGNAL(cellActivated(int,int)),this,SLOT(sectionCellActivated(int,int)));
40 45 this->ui->sectionsList->addAction(exportToSREC_action);
41 46 this->ui->sectionsList->addAction(exportToBIN_action);
42 47 this->ui->symbolsList->addAction(viewSymbolInHexViewer_action);
43 48 this->ui->symbolsList->addAction(exportToSREC_action);
44 49 this->ui->symbolsList->addAction(exportToBIN_action);
45 50 connect(this->exportToBIN_action,SIGNAL(triggered()),this,SLOT(exportToBIN()));
46 51 connect(this->exportToSREC_action,SIGNAL(triggered()),this,SLOT(exportToSREC()));
47 52 connect(this->ui->symbolsFilter,SIGNAL(textChanged(QString)),this,SLOT(filterSymbols(QString)));
48 53 connect(this->ui->caseSensitive,SIGNAL(toggled(bool)),this,SLOT(filterSymbolsCaseUpdate(bool)));
49 54 connect(this->viewSymbolInHexViewer_action,SIGNAL(triggered()),this,SLOT(viewSymbolInHexViewer()));
50 55 this->p_hexviewer = new QHexEdit();
51 56 this->p_hexviewer->setWindowTitle("SocExplorer Hexadecimal viewer");
52 57 this->setWindowTitle("SocExplorer Elf viewer");
53 58 }
54 59
55 60
56 61
57 62 elfFileWidget::~elfFileWidget()
58 63 {
59 64 delete ui;
60 65 delete p_hexviewer;
61 66 }
62 67
63 68
64 69
65 70 void elfFileWidget::setFile(abstractBinFile *file)
66 71 {
67 72 this->p_elf = (ElfFile*)file;
68 73 if(p_elf->isopened() && p_elf->iself())
69 74 {
70 75 this->ui->classLabel->setText(p_elf->getClass());
71 76 this->ui->VersionLabel->setText(QString::number(p_elf->getVersion()));
72 77 this->ui->machineLabel->setText(p_elf->getArchitecture());
73 78 this->ui->endiannesLabel->setText(p_elf->getEndianness());
74 79 this->ui->abiLabel->setText(p_elf->getABI());
75 80 this->ui->entryPointLabel->setText(QString("0x%1").arg((uint)p_elf->getEntryPointAddress(),8,16));
76 81 this->ui->typeLabel->setText(p_elf->getType());
77 82 this->ui->sectionCountLabel->setText(QString::number(p_elf->getSectionCount()));
78 83 this->ui->symbolCountLabel->setText(QString::number(p_elf->getSymbolCount()));
79 84 }
80 85 reloadFile();
81 86 }
82 87
83 88 void elfFileWidget::reloadFile()
84 89 {
85 90 updateSymbols();
86 91 updateSections();
87 92 }
88 93
89 94
90 95
91 96 void elfFileWidget::updateSymbols()
92 97 {
93 98 this->ui->symbolsList->clear();
94 99 this->ui->symbolsList->setRowCount(p_elf->getSymbolCount());
95 100 this->ui->symbolsList->setHorizontalHeaderLabels(QStringList()<<"Index"<<"Value"<<"Size"<<"Type"<<"Link"<<"Section"<<"Name");
96 101 for(int i=0;i<p_elf->getSymbolCount();i++)
97 102 {
98 103 QTableWidgetItem *newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("%1").arg(i),DecimalItem);
99 104 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
100 105 this->ui->symbolsList->setItem(i, 0, newItem);
101 106
102 107 newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("0x%1").arg(p_elf->getSymbolAddress(i),8,16).replace(" ","0"),HexaDecimalItem);
103 108 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
104 109 this->ui->symbolsList->setItem(i, 1, newItem);
105 110
106 111 newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("%1").arg(p_elf->getSymbolSize(i)),DecimalItem);
107 112 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
108 113 this->ui->symbolsList->setItem(i, 2, newItem);
109 114
110 115 newItem = new QTableWidgetItem(p_elf->getSymbolType(i));
111 116 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
112 117 this->ui->symbolsList->setItem(i, 3, newItem);
113 118
114 119 newItem = new QTableWidgetItem(p_elf->getSymbolLinkType(i));
115 120 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
116 121 this->ui->symbolsList->setItem(i, 4, newItem);
117 122
118 123 newItem = new QTableWidgetItem(p_elf->getSymbolSectionName(i));
119 124 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
120 125 this->ui->symbolsList->setItem(i, 5, newItem);
121 126
122 127 newItem = new QTableWidgetItem(p_elf->getSymbolName(i));
123 128 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
124 129 this->ui->symbolsList->setItem(i, 6, newItem);
125 130 }
126 131 this->ui->symbolsList->resizeColumnsToContents();
127 132 }
128 133
129 134
130 135
131 136 void elfFileWidget::updateSections()
132 137 {
133 138 this->ui->sectionsList->clear();
134 139 this->ui->sectionsList->setRowCount(p_elf->getSectionCount());
135 140 this->ui->sectionsList->setHorizontalHeaderLabels(QStringList()<<"Index"<<"Name"<<"Address"<<"Size"<<"File Size"<<"Type");
136 141 for(int i=0;i<p_elf->getSectionCount();i++)
137 142 {
138 143 QTableWidgetItem *newItem = (QTableWidgetItem*) new QTableWidgetIntItem(QString("%1").arg(i),DecimalItem);
139 144 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
140 145 this->ui->sectionsList->setItem(i,0, newItem);
141 146
142 147 newItem = new QTableWidgetItem(p_elf->getSectionName(i));
143 148 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
144 149 this->ui->sectionsList->setItem(i, 1, newItem);
145 150
146 151 newItem = (QTableWidgetItem*) new QTableWidgetIntItem(QString("0x%1").arg(p_elf->getSectionPaddr(i),8,16).replace(" ","0"),HexaDecimalItem);
147 152 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
148 153 this->ui->sectionsList->setItem(i, 2, newItem);
149 154
150 155 newItem = (QTableWidgetItem*) new QTableWidgetIntItem(QString("%1").arg(p_elf->getSectionMemsz(i)),DecimalItem);
151 156 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
152 157 this->ui->sectionsList->setItem(i, 3, newItem);
153 158
154 159 newItem = (QTableWidgetItem*) new QTableWidgetIntItem(QString("%1").arg(p_elf->getSectionDatasz(i)),DecimalItem);
155 160 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
156 161 this->ui->sectionsList->setItem(i, 4, newItem);
157 162
158 163 newItem = new QTableWidgetItem(p_elf->getSectionType(i));
159 164 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
160 165 this->ui->sectionsList->setItem(i, 5, newItem);
161 166 }
162 167 this->ui->sectionsList->resizeColumnsToContents();
163 168 }
164 169
165 170 void elfFileWidget::sectionCellActivated(int row, int column)
166 171 {
167 172 Q_UNUSED(column)
168 173 char* buff=NULL;
169 174 int sectionIndex = p_elf->getSectionIndex(this->ui->sectionsList->item(row,1)->text());
170 175 if(sectionIndex!=-1)
171 176 {
172 177 QString type = p_elf->getSectionType(sectionIndex);
173 178 if(!p_elf->sectionIsNobits(sectionIndex))
174 179 {
175 180 this->p_elf->getSectionData(sectionIndex,&buff);
176 181 this->ui->sectionsHexView->setData(QByteArray(buff,this->p_elf->getSectionDatasz(sectionIndex)));
177 182 this->ui->sectionsHexView->setAddressOffset(this->p_elf->getSectionPaddr(sectionIndex));
178 183 }
179 184 }
180 185 }
181 186
182 187 void elfFileWidget::exportToSREC()
183 188 {
184 189 QList<codeFragment *> fragments;
185 190 if(this->ui->tabWidget->currentWidget()==this->ui->symbolsTab)
186 191 {
187 192 fragments = getSelectedSymbolsFragments();
188 193 }
189 194 if(this->ui->tabWidget->currentWidget()==this->ui->sectionsTab)
190 195 {
191 196 QStringList sectionList=getSelectedSectionsNames();
192 197 if(sectionList.count()>0)
193 198 fragments = p_elf->getFragments(sectionList);
194 199 }
195 200 if(fragments.count()>0)
196 201 {
197 202 QString fileName = QFileDialog::getSaveFileName(this, tr("Save File"),
198 203 NULL,
199 204 tr("SREC Files (*.srec)"));
200 205 if(!fileName.isEmpty())
201 206 {
202 207 srecFile::toSrec(fragments,fileName);
203 208 }
204 209 }
205 210
206 211 }
207 212
208 213 void elfFileWidget::exportToBIN()
209 214 {
210 215 QList<codeFragment *> fragments;
211 216 if(this->ui->tabWidget->currentWidget()==this->ui->symbolsTab)
212 217 {
213 218 fragments = getSelectedSymbolsFragments();
214 219 }
215 220 if(this->ui->tabWidget->currentWidget()==this->ui->sectionsTab)
216 221 {
217 222 QStringList sectionList=getSelectedSectionsNames();
218 223 if(sectionList.count()>0)
219 224 fragments = p_elf->getFragments(sectionList);
220 225 }
221 226 if(fragments.count()>0)
222 227 {
223 228 QString fileName = QFileDialog::getSaveFileName(this, tr("Save File"),
224 229 NULL,
225 230 tr("Binary Files (*.bin)"));
226 231 if(!fileName.isEmpty())
227 232 {
228 233 binaryFile::toBinary(fragments,fileName);
229 234 }
230 235 }
231 236
232 237 }
233 238
234 239 void elfFileWidget::viewSymbolInHexViewer()
235 240 {
236 241 int row=this->ui->symbolsList->item(this->ui->symbolsList->currentRow(),0)->text().toInt();
237 242 int section = p_elf->getSectionIndex(p_elf->getSymbolSectionName(row));
238 243 if(section!=-1)
239 244 {
240 245 qint64 address = p_elf->getSymbolAddress(row);
241 246 qint64 secAddress = p_elf->getSectionPaddr(section);
242 247 qint64 size = p_elf->getSymbolSize(row);
243 248 char* buff=NULL;
244 249 char* symBuff=NULL;
245 250 if(size && !p_elf->sectionIsNobits(section))
246 251 {
247 252 if(section!=-1)
248 253 {
249 254 symBuff = (char*)malloc(size);
250 255 this->p_elf->getSectionData(section,&buff);
251 256 memcpy(symBuff,buff+(address-secAddress),size);
252 257 this->p_hexviewer->setData(QByteArray(symBuff,size));
253 258 this->p_hexviewer->setAddressOffset(address);
254 259 this->p_hexviewer->show();
255 260 }
256 261 }
257 262 }
258 263
259 264 }
260 265
261 266 void elfFileWidget::filterSymbols(const QString &pattern)
262 267 {
263 268 Qt::MatchFlags flag = Qt::MatchContains | Qt::MatchStartsWith | Qt::MatchEndsWith | Qt::MatchRegExp | Qt::MatchWildcard | Qt::MatchWrap |Qt::MatchRecursive;
264 269 if(this->ui->caseSensitive->isChecked())
265 270 flag |= Qt::MatchCaseSensitive;
266 271 if(pattern.isEmpty())
267 272 {
268 273 for(int i=0;i<this->ui->symbolsList->rowCount();i++)
269 274 this->ui->symbolsList->setRowHidden(i,false);
270 275 }
271 276 else
272 277 {
273 278 for(int i=0;i<this->ui->symbolsList->rowCount();i++)
274 279 this->ui->symbolsList->setRowHidden(i,true);
275 280 QList<QTableWidgetItem*> items = this->ui->symbolsList->findItems(pattern,flag);
276 281 for(int i=0;i<items.count();i++)
277 282 this->ui->symbolsList->setRowHidden(items.at(i)->row(),false);
278 283 }
279 284 }
280 285
281 286 void elfFileWidget::filterSymbolsCaseUpdate(bool toggled)
282 287 {
283 288 Q_UNUSED(toggled)
284 289 this->filterSymbols(this->ui->symbolsFilter->text());
285 290 }
286 291
287 292 QList<codeFragment *> elfFileWidget::getSelectedSymbolsFragments()
288 293 {
289 294 QList<codeFragment *> fragments;
290 295 codeFragment * fragment;
291 296 if(p_elf->isopened())
292 297 {
293 298 QList<QTableWidgetItem*> items = this->ui->symbolsList->selectedItems();
294 299 for(int i=0;i<items.count();i++)
295 300 {
296 301 int row=this->ui->symbolsList->item(items.at(i)->row(),0)->text().toInt();
297 302 int section = p_elf->getSectionIndex(p_elf->getSymbolSectionName(row));
298 303 if(section!=-1)
299 304 {
300 305 qint64 address = p_elf->getSymbolAddress(row);
301 306 qint64 secAddress = p_elf->getSectionPaddr(section);
302 307 qint64 size = p_elf->getSymbolSize(row);
303 308 char* buff=NULL;
304 309 if(size && !p_elf->sectionIsNobits(section))
305 310 {
306 311 if(section!=-1)
307 312 {
308 313 fragment= new codeFragment();
309 314 fragment->data = (char*)malloc(size);
310 315 fragment->address = address;
311 316 fragment->size = size;
312 317 this->p_elf->getSectionData(section,&buff);
313 318 memcpy(fragment->data,buff+(address-secAddress),size);
314 319 fragments.append(fragment);
315 320 }
316 321 }
317 322 }
318 323
319 324 }
320 325 }
321 326 return fragments;
322 327
323 328 }
324 329
325 330
326 331
327 332 QStringList elfFileWidget::getSelectedSectionsNames()
328 333 {
329 334 QStringList sectionList;
330 335 QList<QTableWidgetItem*> items = this->ui->sectionsList->selectedItems();
331 336 for(int i=0;i<items.count();i++)
332 337 {
333 338 QString section = p_elf->getSectionName(items.at(i)->row());
334 339 if(!sectionList.contains(section))
335 340 {
336 341 sectionList.append(section);
337 342 }
338 343 }
339 344 return sectionList;
340 345 }
341 346
342 347
343 348
344 349
345 350
346 351
347 352
348 353
349 354
350 355
351 356
352 357
353 358
354 359
@@ -1,66 +1,71
1 1 /*------------------------------------------------------------------------------
2 2 -- This file is a part of the SocExplorer Software
3 3 -- Copyright (C) 2014, Plasma Physics Laboratory - CNRS
4 4 --
5 5 -- This program is free software; you can redistribute it and/or modify
6 6 -- it under the terms of the GNU General Public License as published by
7 7 -- the Free Software Foundation; either version 2 of the License, or
8 8 -- (at your option) any later version.
9 9 --
10 10 -- This program is distributed in the hope that it will be useful,
11 11 -- but WITHOUT ANY WARRANTY; without even the implied warranty of
12 12 -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 13 -- GNU General Public License for more details.
14 14 --
15 15 -- You should have received a copy of the GNU General Public License
16 16 -- along with this program; if not, write to the Free Software
17 17 -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 18 -------------------------------------------------------------------------------*/
19 19 /*-- Author : Alexis Jeandet
20 20 -- Mail : alexis.jeandet@member.fsf.org
21 21 ----------------------------------------------------------------------------*/
22 22 #ifndef ELFFILEWIDGET_H
23 23 #define ELFFILEWIDGET_H
24 24
25 #include <QtWidgets/QWidget>
25 #if QT_VERSION >= 0x050000
26 #include <QtWidgets/QWidget>
27 #include <QtWidgets/QAction>
28 #else
29 #include <QWidget>
30 #include <QAction>
31 #endif
26 32 #include "elffile.h"
27 #include <QtWidgets/QAction>
28 33 #include <qhexedit.h>
29 34
30 35 namespace Ui {
31 36 class elfFileWidget;
32 37 }
33 38
34 39 class elfFileWidget : public abstractBinFileWidget
35 40 {
36 41 Q_OBJECT
37 42
38 43 public:
39 44 explicit elfFileWidget(QWidget *parent = 0);
40 45 ~elfFileWidget();
41 46
42 47 public slots:
43 48 void setFile(abstractBinFile* file);
44 49 void reloadFile();
45 50 void updateSymbols();
46 51 void updateSections();
47 52
48 53 private slots:
49 54 void sectionCellActivated(int row, int column);
50 55 void exportToSREC();
51 56 void exportToBIN();
52 57 void viewSymbolInHexViewer();
53 58 void filterSymbols(const QString& pattern);
54 59 void filterSymbolsCaseUpdate(bool toggled);
55 60 private:
56 61 QList<codeFragment*> getSelectedSymbolsFragments();
57 62 Ui::elfFileWidget *ui;
58 63 QStringList getSelectedSectionsNames();
59 64 ElfFile* p_elf;
60 65 QAction* exportToSREC_action;
61 66 QAction* exportToBIN_action;
62 67 QAction* viewSymbolInHexViewer_action;
63 68 QHexEdit* p_hexviewer;
64 69 };
65 70
66 71 #endif // ELFFILEWIDGET_H
@@ -1,64 +1,75
1 1 /*------------------------------------------------------------------------------
2 2 -- This file is a part of the SocExplorer Software
3 3 -- Copyright (C) 2013, Plasma Physics Laboratory - CNRS
4 4 --
5 5 -- This program is free software; you can redistribute it and/or modify
6 6 -- it under the terms of the GNU General Public License as published by
7 7 -- the Free Software Foundation; either version 3 of the License, or
8 8 -- (at your option) any later version.
9 9 --
10 10 -- This program is distributed in the hope that it will be useful,
11 11 -- but WITHOUT ANY WARRANTY; without even the implied warranty of
12 12 -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 13 -- GNU General Public License for more details.
14 14 --
15 15 -- You should have received a copy of the GNU General Public License
16 16 -- along with this program; if not, write to the Free Software
17 17 -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 18 -------------------------------------------------------------------------------*/
19 19 /*-- Author : Alexis Jeandet
20 20 -- Mail : alexis.jeandet@lpp.polytechnique.fr
21 21 ----------------------------------------------------------------------------*/
22 22 #ifndef ELFINFOWDGT_H
23 23 #define ELFINFOWDGT_H
24 24
25 #include <QtWidgets/QWidget>
25 #if QT_VERSION >= 0x050000
26 #include <QtWidgets/QWidget>
27 #include <QtWidgets/QVBoxLayout>
28 #include <QtWidgets/QHBoxLayout>
29 #include <QtWidgets/QLabel>
30 #include <QtWidgets/QTextEdit>
31 #include <QtWidgets/QTableWidget>
32 #include <QtWidgets/QSplitter>
33 #else
34 #include <QWidget>
35 #include <QVBoxLayout>
36 #include <QHBoxLayout>
37 #include <QLabel>
38 #include <QTextEdit>
39 #include <QTableWidget>
40 #include <QSplitter>
41 #endif
42
26 43 #include "elfparser.h"
27 #include <QtWidgets/QVBoxLayout>
28 #include <QtWidgets/QHBoxLayout>
29 #include <QtWidgets/QLabel>
30 #include <QtWidgets/QTextEdit>
31 #include <QtWidgets/QTableWidget>
32 44 #include <qhexedit.h>
33 #include <QtWidgets/QSplitter>
34 45
35 46 class elfInfoWdgt : public QWidget
36 47 {
37 48 Q_OBJECT
38 49 public:
39 50 explicit elfInfoWdgt(QWidget *parent = 0);
40 51
41 52 signals:
42 53
43 54
44 55 public slots:
45 56 void updateInfo(elfparser* parser);
46 57 void cellActivated ( int row, int column );
47 58
48 59 private:
49 60 void updateSectionsTable(elfparser* parser);
50 61 void updateSegmentsTable(elfparser* parser);
51 62 QVBoxLayout* mainLayout;
52 63 QLabel* ElfArchitecture;
53 64 QLabel* ElfType;
54 65 QLabel* ElfVersion;
55 66 QTableWidget* segmentsListTableWdgt,*sectionsListTableWdgt;
56 67 QHexEdit* hexViewer;
57 68 QSplitter* splitter;
58 69 QWidget* elfInfoWdgtLay;
59 70 QVBoxLayout* elfInfoWdgtLayout;
60 71 elfparser* parser;
61 72
62 73 };
63 74
64 75 #endif // ELFINFOWDGT_H
@@ -1,522 +1,524
1 1 /*------------------------------------------------------------------------------
2 2 -- This file is a part of the SocExplorer Software
3 3 -- Copyright (C) 2013, Plasma Physics Laboratory - CNRS
4 4 --
5 5 -- This program is free software; you can redistribute it and/or modify
6 6 -- it under the terms of the GNU General Public License as published by
7 7 -- the Free Software Foundation; either version 3 of the License, or
8 8 -- (at your option) any later version.
9 9 --
10 10 -- This program is distributed in the hope that it will be useful,
11 11 -- but WITHOUT ANY WARRANTY; without even the implied warranty of
12 12 -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 13 -- GNU General Public License for more details.
14 14 --
15 15 -- You should have received a copy of the GNU General Public License
16 16 -- along with this program; if not, write to the Free Software
17 17 -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 18 -------------------------------------------------------------------------------*/
19 19 /*-- Author : Alexis Jeandet
20 20 -- Mail : alexis.jeandet@lpp.polytechnique.fr
21 21 ----------------------------------------------------------------------------*/
22 22 #include "elfparser.h"
23 23 #include <sys/types.h>
24 24 #include <sys/stat.h>
25 25 #include <fcntl.h>
26 26 #include <unistd.h>
27 27
28 28 extern QString elfresolveMachine(Elf64_Half e_machine);
29 29
30 30
31 31 elfparser::elfparser()
32 32 {
33 33 this->opened = false;
34 34 this->type_elf = false;
35 35 this->elfFile = (int)NULL;
36 36 this->e = NULL;
37 37 }
38 38
39 39
40 40 int elfparser::setFilename(const QString &name)
41 41 {
42 42 this->closeFile();
43 43 if(elf_version(EV_CURRENT)==EV_NONE)return 0;
44 44 #ifdef _ELF_WINDOWS_
45 45 this->elfFile = open(name.toStdString().c_str(),O_RDONLY|O_BINARY ,0);
46 46 #else
47 47 this->elfFile = open(name.toStdString().c_str(),O_RDONLY ,0);
48 48 #endif
49 49 if(this->elfFile==(int)NULL)return 0;
50 50 this->e = elf_begin(this->elfFile,ELF_C_READ,NULL);
51 51 if(this->e==NULL)return 0;
52 52 this->ek = elf_kind(this->e);
53 53 gelf_getehdr (this->e, &this->ehdr );
54 54 elf_getshdrstrndx (this->e, &this->shstrndx);
55 55 this->updateSegments();
56 56 this->updateSections();
57 57 return 1;
58 58 }
59 59
60 60
61 61 int elfparser::closeFile()
62 62 {
63 63 if(this->elfFile!=(int)NULL)
64 64 {
65 65 if(this->e!=NULL)
66 66 {
67 67 elf_end(this->e);
68 68 this->e = NULL;
69 69 }
70 70 close(this->elfFile);
71 71 this->elfFile = (int)NULL;
72 72 }
73 73 return 0;
74 74 }
75 75
76 76 QString elfparser::getClass()
77 77 {
78 78 if(this->e!=NULL)
79 79 {
80 80 int eclass = gelf_getclass(this->e);
81 81 if(eclass==ELFCLASS32)return "ELF32";
82 82 if(eclass==ELFCLASS64)return "ELF64";
83 83 }
84 84 return "none";
85 85 }
86 86
87 87
88 88 bool elfparser::isopened()
89 89 {
90 90 return this->opened;
91 91 }
92 92
93 93
94 94 bool elfparser::iself()
95 95 {
96 96 return this->type_elf;
97 97 }
98 98
99 99
100 100 QString elfparser::getArchitecture()
101 101 {
102 102 if(this->e!=NULL)
103 103 {
104 104 return elfresolveMachine(this->ehdr.e_machine);
105 105 }
106 106 return "";
107 107 }
108 108
109 109
110 110 QString elfparser::getType()
111 111 {
112 112 QString kind("");
113 113 if(this->e!=NULL)
114 114 {
115 115 switch(this->ek)
116 116 {
117 117 case ELF_K_AR:
118 118 kind = "Archive";
119 119 break;
120 120 case ELF_K_ELF:
121 121 kind = "Elf";
122 122 break;
123 123 case ELF_K_COFF:
124 124 kind = "COFF";
125 125 break;
126 126 case ELF_K_NUM:
127 127 kind = "NUM";
128 128 break;
129 129 case ELF_K_NONE:
130 130 kind = "Data";
131 131 break;
132 132 default:
133 133 kind = "Unknow";
134 134 break;
135 135 }
136 136 }
137 137 return kind;
138 138 }
139 139
140 140 QString elfparser::getEndianness()
141 141 {
142 142 if(this->e!=NULL)
143 143 {
144 144 if(this->ehdr.e_ident[EI_DATA]==ELFDATA2LSB)return "2's complement, little endian";
145 145 if(this->ehdr.e_ident[EI_DATA]==ELFDATA2MSB)return "2's complement, big endian";
146 146 }
147 147 return "none";
148 148 }
149 149
150 150 QString elfparser::getABI()
151 151 {
152 152 if(this->e!=NULL)
153 153 {
154 154 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_NONE)return "UNIX System V ABI";
155 155 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_SYSV)return "Alias";
156 156 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_HPUX)return "HP-UX";
157 157 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_NETBSD)return "NetBSD";
158 158 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_LINUX)return "Object uses GNU ELF extensions";
159 159 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_SOLARIS)return "Sun Solaris";
160 160 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_AIX)return "IBM AIX";
161 161 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_IRIX)return "SGI Irix";
162 162 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_FREEBSD)return "FreeBSD";
163 163 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_TRU64)return "Compaq TRU64 UNIX";
164 164 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_MODESTO)return " Novell Modesto";
165 165 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_OPENBSD)return "OpenBSD";
166 #ifdef ELFOSABI_ARM_AEABI
166 167 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_ARM_AEABI)return "ARM EABI";
168 #endif
167 169 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_ARM)return "ARM";
168 170 if(this->ehdr.e_ident[EI_OSABI]==ELFOSABI_STANDALONE)return "Standalone (embedded) application";
169 171 }
170 172 return "none";
171 173 }
172 174
173 175
174 176 qint64 elfparser::getVersion()
175 177 {
176 178 if(this->e!=NULL)
177 179 {
178 180 return this->ehdr.e_version;
179 181 }
180 182 return -1;
181 183 }
182 184
183 185 qint64 elfparser::getEntryPointAddress()
184 186 {
185 187 if(this->e!=NULL)
186 188 {
187 189 return this->ehdr.e_entry;
188 190 }
189 191 return -1;
190 192 }
191 193
192 194
193 195 int elfparser::getSectioncount()
194 196 {
195 197 return (int)this->SectionCount;
196 198 }
197 199
198 200
199 201 int elfparser::getSegmentcount()
200 202 {
201 203 return (int)this->SegmentCount;
202 204 }
203 205
204 206
205 207 QString elfparser::getSegmentType(int index)
206 208 {
207 209 QString type("");
208 210 if(this->e!=NULL)
209 211 {
210 212 if(index < this->Segments.count())
211 213 {
212 214 switch(this->Segments.at(index)->p_type)
213 215 {
214 216 case PT_NULL:
215 217 type = "Program header table entry unused";
216 218 break;
217 219 case PT_LOAD:
218 220 type = "Loadable program segment";
219 221 break;
220 222 case PT_DYNAMIC :
221 223 type = "Dynamic linking information";
222 224 break;
223 225 case PT_INTERP:
224 226 type ="Program interpreter";
225 227 break;
226 228 case PT_NOTE:
227 229 type = "Auxiliary information";
228 230 break;
229 231 case PT_SHLIB:
230 232 type = "Reserved";
231 233 break;
232 234 case PT_PHDR:
233 235 type = "Entry for header table itself";
234 236 break;
235 237 case PT_TLS:
236 238 type = "Thread-local storage segment";
237 239 break;
238 240 case PT_NUM:
239 241 type = "Number of defined types";
240 242 break;
241 243 case PT_LOOS:
242 244 type = "Start of OS-specific";
243 245 break;
244 246 case PT_SUNWSTACK:
245 247 type = "Stack segment";
246 248 break;
247 249 case PT_LOPROC:
248 250 type = "Start of processor-specific";
249 251 break;
250 252 case PT_HIPROC:
251 253 type = "End of processor-specific";
252 254 break;
253 255 default:
254 256 type = "Unknow Section Type";
255 257 break;
256 258 }
257 259 }
258 260 }
259 261
260 262 return type;
261 263 }
262 264
263 265
264 266 qint64 elfparser::getSegmentOffset(int index)
265 267 {
266 268 qint64 Offset=-1;
267 269 if(this->e!=NULL)
268 270 {
269 271 if(index < this->Segments.count())
270 272 {
271 273 Offset = (qint64)this->Segments.at(index)->p_offset;
272 274 }
273 275 }
274 276 return Offset;
275 277 }
276 278
277 279
278 280 qint64 elfparser::getSegmentVaddr(int index)
279 281 {
280 282 int64_t Vaddr = 0;
281 283 if(this->e!=NULL)
282 284 {
283 285 if(index < this->Segments.count())
284 286 {
285 287 Vaddr = (int64_t)this->Segments.at(index)->p_vaddr;
286 288 }
287 289 }
288 290 return Vaddr;
289 291 }
290 292
291 293
292 294 qint64 elfparser::getSegmentPaddr(int index)
293 295 {
294 296 int64_t Paddr=0;
295 297 if(this->e!=NULL)
296 298 {
297 299 if(index < this->Segments.count())
298 300 {
299 301 Paddr = (int64_t)this->Segments.at(index)->p_paddr;
300 302 }
301 303 }
302 304 return Paddr;
303 305 }
304 306
305 307 qint64 elfparser::getSectionPaddr(int index)
306 308 {
307 309 int64_t Paddr=0;
308 310 if(this->e!=NULL)
309 311 {
310 312 if(index < this->sections.count())
311 313 {
312 314 Paddr = (int64_t)this->sections.at(index)->section_header->sh_addr;
313 315 }
314 316 }
315 317 return Paddr;
316 318 }
317 319
318 320
319 321 qint64 elfparser::getSegmentFilesz(int index)
320 322 {
321 323 int64_t FileSz=0;
322 324 if(this->e!=NULL)
323 325 {
324 326 if(index < this->Segments.count())
325 327 {
326 328 FileSz = (int64_t)this->Segments.at(index)->p_filesz;
327 329 }
328 330 }
329 331 return FileSz;
330 332 }
331 333
332 334 qint64 elfparser::getSectionDatasz(int index)
333 335 {
334 336 int64_t DataSz=0;
335 337 if(this->e!=NULL)
336 338 {
337 339 if(index < this->sections.count())
338 340 {
339 341 DataSz = (int64_t)this->sections.at(index)->data->d_size;
340 342 }
341 343 }
342 344 return DataSz;
343 345 }
344 346
345 347 bool elfparser::getSectionData(int index, char **buffer)
346 348 {
347 349 if(this->e!=NULL)
348 350 {
349 351 if(index < this->sections.count())
350 352 {
351 353 *buffer = (char *)this->sections.at(index)->data->d_buf;
352 354 return true;
353 355 }
354 356 }
355 357 return false;
356 358 }
357 359
358 360
359 361 qint64 elfparser::getSegmentMemsz(int index)
360 362 {
361 363 int64_t MemSz=0;
362 364 if(this->e!=NULL)
363 365 {
364 366 if(index < this->Segments.count())
365 367 {
366 368 MemSz = (int64_t)this->Segments.at(index)->p_memsz;
367 369 }
368 370 }
369 371 return MemSz;
370 372 }
371 373
372 374 qint64 elfparser::getSectionMemsz(int index)
373 375 {
374 376 int64_t MemSz=0;
375 377 if(this->e!=NULL)
376 378 {
377 379 if(index < this->sections.count())
378 380 {
379 381 MemSz = (int64_t)this->sections.at(index)->section_header->sh_size;
380 382 }
381 383 }
382 384 return MemSz;
383 385 }
384 386
385 387
386 388 QString elfparser::getSegmentFlags(int index)
387 389 {
388 390 QString flags("");
389 391 if(this->e!=NULL)
390 392 {
391 393 if(index < this->Segments.count())
392 394 {
393 395 if((this->Segments.at(index)->p_flags&PF_X) == PF_X)flags+="x";
394 396 if((this->Segments.at(index)->p_flags&PF_W) == PF_W)flags+="w";
395 397 if((this->Segments.at(index)->p_flags&PF_R) == PF_R)flags+="r";
396 398 if((this->Segments.at(index)->p_flags&PF_MASKOS) == PF_MASKOS)flags+=" OS-specific";
397 399 if((this->Segments.at(index)->p_flags&PF_MASKPROC) == PF_MASKPROC)flags+=" Processor-specific";
398 400 }
399 401 }
400 402 return flags;
401 403 }
402 404
403 405
404 406 QString elfparser::getSectionName(int index)
405 407 {
406 408 char* nameChr = elf_strptr(this->e , this->shstrndx , this->sections.at(index)->section_header->sh_name);
407 409 return QString(nameChr);
408 410 }
409 411
410 412
411 413 void elfparser::updateSections()
412 414 {
413 415 for(int i=0;i<this->sections.count();i++)
414 416 {
415 417 delete this->sections.at(i);
416 418 }
417 419 this->sections.clear();
418 420 this->scn = elf_nextscn (this->e , NULL );
419 421 this->SectionCount = 0;
420 422 while( this->scn != NULL )
421 423 {
422 424 GElf_Shdr* shdr = (GElf_Shdr*)malloc(sizeof(GElf_Shdr));
423 425 gelf_getshdr ( this->scn , shdr );
424 426 Elf_Data* data = elf_getdata(this->scn, NULL);
425 427 this->sections.append(new Elf_Section(data,shdr));
426 428 this->SectionCount+=1;
427 429 this->scn = elf_nextscn(e , scn);
428 430 }
429 431 }
430 432
431 433
432 434 void elfparser::updateSegments()
433 435 {
434 436 elf_getphdrnum (this->e , &this->SegmentCount);
435 437 for(int i=0;i<this->Segments.count();i++)
436 438 {
437 439 free(this->Segments.at(i));
438 440 }
439 441 this->Segments.clear();
440 442 for(int i=0;i<(int)this->SegmentCount;i++)
441 443 {
442 444 GElf_Phdr* header=(GElf_Phdr*)malloc(sizeof(GElf_Phdr));
443 445 gelf_getphdr (this->e , i , header );
444 446 this->Segments.append(header);
445 447 }
446 448 }
447 449
448 450
449 451
450 452
451 453
452 454 QString elfparser::getSectionType(int index)
453 455 {
454 456 QString type("");
455 457 if(this->e!=NULL)
456 458 {
457 459 if(index < this->Segments.count())
458 460 {
459 461 switch(this->Segments.at(index)->p_type)
460 462 {
461 463 case SHT_NULL : type = "Section header table entry unused"; break;
462 464 case SHT_PROGBITS : type = "Program data"; break;
463 465 case SHT_SYMTAB : type = "Symbol table"; break;
464 466 case SHT_STRTAB : type = "String table"; break;
465 467 case SHT_RELA : type = "Relocation entries with addends"; break;
466 468 case SHT_HASH : type = "Symbol hash table"; break;
467 469 case SHT_DYNAMIC : type = "Dynamic linking information"; break;
468 470 case SHT_NOTE : type = "Notes"; break;
469 471 case SHT_NOBITS :type = "Program space with no data (bss)"; break;
470 472 case SHT_REL :type = "Relocation entries, no addends"; break;
471 473 case SHT_SHLIB : type = "Reserved"; break;
472 474 case SHT_DYNSYM : type = "Dynamic linker symbol table"; break;
473 475 case SHT_INIT_ARRAY : type = "Array of constructors"; break;
474 476 case SHT_FINI_ARRAY : type = "Array of destructors"; break;
475 477 case SHT_PREINIT_ARRAY : type = "Array of pre-constructors"; break;
476 478 case SHT_GROUP : type = "Section group"; break;
477 479 case SHT_SYMTAB_SHNDX : type = "Extended section indeces"; break;
478 480 case SHT_NUM : type = "Number of defined types. "; break;
479 481 case SHT_LOOS : type = "Start OS-specific. "; break;
480 482 case SHT_LOSUNW : type = "Sun-specific low bound. "; break;
481 483 case SHT_SUNW_COMDAT : type = " "; break;
482 484 case SHT_SUNW_syminfo : type = " "; break;
483 485 case SHT_GNU_verdef : type = "Version definition section. "; break;
484 486 case SHT_GNU_verneed : type = "Version needs section. "; break;
485 487 case SHT_GNU_versym : type = "Version symbol table. "; break;
486 488 case SHT_LOPROC : type = "Start of processor-specific"; break;
487 489 case SHT_HIPROC : type = "End of processor-specific"; break;
488 490 case SHT_HIUSER : type = "End of application-specific"; break;
489 491 }
490 492 }
491 493 }
492 494 return type;
493 495 }
494 496
495 497 bool elfparser::isElf(const QString &File)
496 498 {
497 499 int file =0;
498 500 #ifdef _ELF_WINDOWS_
499 501 file = open(File.toStdString().c_str(),O_RDONLY|O_BINARY ,0);
500 502 #else
501 503 file = open(File.toStdString().c_str(),O_RDONLY ,0);
502 504 #endif
503 505 char Magic[4];
504 506 if(file!=-1)
505 507 {
506 508 size_t res = read(file,Magic,4);
507 509 close(file);
508 510 if((res == 4) && (Magic[0]==0x7f) && (Magic[1]==0x45) && (Magic[2]==0x4c) && (Magic[3]==0x46))
509 511 {
510 512 return true;
511 513 }
512 514 }
513 515 return false;
514 516 }
515 517
516 518
517 519
518 520
519 521
520 522
521 523
522 524
@@ -1,37 +1,38
1 1 #include "filelist.h"
2 2 #include <QMimeData>
3 #include <QUrl>
3 4
4 5 FileList::FileList(QWidget *parent) :
5 6 QTableWidget(parent)
6 7 {
7 8 setHorizontalHeaderLabels(QStringList()<<"File"<<"Type");
8 9 this->setAcceptDrops(true);
9 10 }
10 11
11 12 void FileList::dragEnterEvent(QDragEnterEvent *event)
12 13 {
13 14 event->acceptProposedAction();
14 15 }
15 16
16 17 void FileList::dragMoveEvent(QDragMoveEvent *event)
17 18 {
18 19 event->acceptProposedAction();
19 20 }
20 21
21 22 void FileList::dropEvent(QDropEvent *event)
22 23 {
23 24 const QMimeData* mimeData = event->mimeData();
24 25
25 26 if (mimeData->hasUrls())
26 27 {
27 28 QStringList pathList;
28 29 QList<QUrl> urlList = mimeData->urls();
29 30
30 31 for (int i = 0; i < urlList.size() && i < 32; ++i)
31 32 {
32 33 pathList.append(urlList.at(i).toLocalFile());
33 34 }
34 35 emit openFiles(pathList);
35 36 event->acceptProposedAction();
36 37 }
37 38 }
@@ -1,144 +1,148
1 1 /*------------------------------------------------------------------------------
2 2 -- This file is a part of the SocExplorer Software
3 3 -- Copyright (C) 2014, Plasma Physics Laboratory - CNRS
4 4 --
5 5 -- This program is free software; you can redistribute it and/or modify
6 6 -- it under the terms of the GNU General Public License as published by
7 7 -- the Free Software Foundation; either version 2 of the License, or
8 8 -- (at your option) any later version.
9 9 --
10 10 -- This program is distributed in the hope that it will be useful,
11 11 -- but WITHOUT ANY WARRANTY; without even the implied warranty of
12 12 -- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 13 -- GNU General Public License for more details.
14 14 --
15 15 -- You should have received a copy of the GNU General Public License
16 16 -- along with this program; if not, write to the Free Software
17 17 -- Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 18 -------------------------------------------------------------------------------*/
19 19 /*-- Author : Alexis Jeandet
20 20 -- Mail : alexis.jeandet@member.fsf.org
21 21 ----------------------------------------------------------------------------*/
22 22 #include "srecfilewidget.h"
23 23 #include "ui_srecfilewidget.h"
24 24 #include <QTableWidgetItem>
25 25 #include <qtablewidgetintitem.h>
26 #include <QtWidgets/QFileDialog>
26 #if QT_VERSION >= 0x050000
27 #include <QtWidgets/QFileDialog>
28 #else
29 #include <QFileDialog>
30 #endif
27 31 #include "binaryfile.h"
28 32
29 33 srecFileWidget::srecFileWidget(QWidget *parent) :
30 34 abstractBinFileWidget(parent),
31 35 ui(new Ui::srecFileWidget)
32 36 {
33 37 ui->setupUi(this);
34 38 connect(this->ui->fragmentsList,SIGNAL(cellActivated(int,int)),this,SLOT(recordCellActivated(int,int)));
35 39 this->setWindowTitle("SocExplorer SREC viewer");
36 40 exportToSREC_action = new QAction(tr("Export to SREC"),this);
37 41 exportToBIN_action = new QAction(tr("Export to Binary"),this);
38 42 this->ui->fragmentsList->addAction(exportToBIN_action);
39 43 this->ui->fragmentsList->addAction(exportToSREC_action);
40 44 connect(this->exportToBIN_action,SIGNAL(triggered()),this,SLOT(exportToBIN()));
41 45 connect(this->exportToSREC_action,SIGNAL(triggered()),this,SLOT(exportToSREC()));
42 46 }
43 47
44 48 srecFileWidget::~srecFileWidget()
45 49 {
46 50 delete ui;
47 51 }
48 52
49 53 void srecFileWidget::setFile(abstractBinFile *file)
50 54 {
51 55 this->p_srec = (srecFile*)file;
52 56 if(p_srec->isopened() && p_srec->isSREC())
53 57 {
54 58 reloadFile();
55 59 }
56 60 }
57 61
58 62 void srecFileWidget::reloadFile()
59 63 {
60 64 this->ui->fragmentsList->clear();
61 65 this->ui->fragmentsList->setRowCount(p_srec->getFragmentsCount());
62 66 this->ui->fragmentsList->setHorizontalHeaderLabels(QStringList()<<"Index"<<"Address"<<"Size"<<"Header");
63 67 for(int i=0;i<p_srec->getFragmentsCount();i++)
64 68 {
65 69 QTableWidgetItem *newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("%1").arg(i),DecimalItem);
66 70 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
67 71 this->ui->fragmentsList->setItem(i, 0, newItem);
68 72
69 73 newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("0x%1").arg(p_srec->getFragmentAddress(i),8,16).replace(" ","0"),HexaDecimalItem);
70 74 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
71 75 this->ui->fragmentsList->setItem(i, 1, newItem);
72 76
73 77 newItem = (QTableWidgetItem*)new QTableWidgetIntItem(QString("%1").arg(p_srec->getFragmentSize(i)),DecimalItem);
74 78 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
75 79 this->ui->fragmentsList->setItem(i, 2, newItem);
76 80
77 81 newItem = new QTableWidgetItem(p_srec->getFragmentHeader(i));
78 82 newItem->setFlags(newItem->flags() ^ Qt::ItemIsEditable);
79 83 this->ui->fragmentsList->setItem(i, 3, newItem);
80 84
81 85 }
82 86 this->ui->fragmentsList->resizeColumnsToContents();
83 87 }
84 88
85 89 void srecFileWidget::recordCellActivated(int row, int column)
86 90 {
87 91 Q_UNUSED(column)
88 92 char* buff=NULL;
89 93 int index = this->ui->fragmentsList->item(row,0)->text().toInt();
90 94 if(index!=-1)
91 95 {
92 96 this->p_srec->getFragmentData(index,&buff);
93 97 this->ui->fragmentHexView->setData(QByteArray(buff,this->p_srec->getFragmentSize(index)));
94 98 this->ui->fragmentHexView->setAddressOffset(this->p_srec->getFragmentAddress(index));
95 99 }
96 100
97 101 }
98 102
99 103 void srecFileWidget::exportToSREC()
100 104 {
101 105 QList<codeFragment *> SelectedFragmentsList=getSelectedFragments();
102 106 if(SelectedFragmentsList.count()>0)
103 107 {
104 108 QString fileName = QFileDialog::getSaveFileName(this, tr("Save File"),
105 NULL,
106 tr("SREC Files (*.srec)"));
109 NULL,
110 tr("SREC Files (*.srec)"));
107 111 if(!fileName.isEmpty())
108 112 {
109 113 srecFile::toSrec(SelectedFragmentsList,fileName);
110 114 }
111 115 }
112 116 }
113 117
114 118 void srecFileWidget::exportToBIN()
115 119 {
116 120 QList<codeFragment *> SelectedFragmentsList=getSelectedFragments();
117 121 if(SelectedFragmentsList.count()>0)
118 122 {
119 123 QString fileName = QFileDialog::getSaveFileName(this, tr("Save File"),
120 NULL,
121 tr("Binary Files (*.bin)"));
124 NULL,
125 tr("Binary Files (*.bin)"));
122 126 if(!fileName.isEmpty())
123 127 {
124 128 binaryFile::toBinary(SelectedFragmentsList,fileName);
125 129 }
126 130 }
127 131 }
128 132
129 133 QList<codeFragment *> srecFileWidget::getSelectedFragments()
130 134 {
131 135 QList<codeFragment *> SelectedFragmentsList;
132 136 QList<QTableWidgetItem*> items = this->ui->fragmentsList->selectedItems();
133 137 for(int i=0;i<items.count();i++)
134 138 {
135 139 codeFragment * fragment = p_srec->getFragment(items.at(i)->row());
136 140 if(!SelectedFragmentsList.contains(fragment))
137 141 {
138 142 SelectedFragmentsList.append(fragment);
139 143 }
140 144 }
141 145 return SelectedFragmentsList;
142 146 }
143 147
144 148
General Comments 0
You need to be logged in to leave comments. Login now