Example #1
0
void dspIndentedBOM::sFillList()
{
  _bomitem->clear();
  
  if (_item->isValid())
  {
	q.prepare("SELECT * FROM indentedBOM(:item_id, :revision_id, :expired, :effective) "
		      "WHERE (bomdata_item_id > 0);");
    q.bindValue(":item_id", _item->id());
    q.bindValue(":revision_id", _revision->id());
    if (!_showExpired->isChecked())
	  q.bindValue(":expired", 0);
	else
      q.bindValue(":expired", _expiredDays->value());
    if (!_showFuture->isChecked())
      q.bindValue(":effective", 0);
	else
      q.bindValue(":effective", _effectiveDays->value());
    q.exec();

    QStack<XTreeWidgetItem*> parent;
    XTreeWidgetItem *last = 0;
    int level = 1;
    while(q.next())
    {
      // If the level this item is on is lower than the last level we just did then we need
      // to pop the stack a number of times till we are equal.
      while(q.value("bomdata_bomwork_level").toInt() < level)
      {
        level--;
        last = parent.pop();
      }

      // If the level this item is on is higher than the last level we need to push the last
      // item onto the stack a number of times till we are equal. (Should only ever be 1.)
      while(q.value("bomdata_bomwork_level").toInt() > level)
      {
        level++;
        parent.push(last);
        last = 0;
      }

      // If there is an item in the stack use that as the parameter to the new xlistviewitem
      // otherwise we'll just use the xlistview _layout
      if(!parent.isEmpty() && parent.top())
        last = new XTreeWidgetItem(parent.top(), last, q.value("bomdata_bomwork_id").toInt(),
                                    q.value("bomdata_bomwork_seqnumber"), q.value("bomdata_item_number"),
                                    q.value("bomdata_itemdescription"), q.value("bomdata_uom_name"),
                                    q.value("bomdata_qtyper"), q.value("bomdata_scrap"),
                                    q.value("bomdata_effective"), q.value("bomdata_expires") );
      else
        last = new XTreeWidgetItem(_bomitem, last, q.value("bomdata_bomwork_id").toInt(),
                                    q.value("bomdata_bomwork_seqnumber"), q.value("bomdata_item_number"),
                                    q.value("bomdata_itemdescription"), q.value("bomdata_uom_name"),
                                    q.value("bomdata_qtyper"), q.value("bomdata_scrap"),
                                    q.value("bomdata_effective"), q.value("bomdata_expires") );
	          
	  if (q.value("bomdata_expired").toBool())
        last->setTextColor("red");
      else if (q.value("bomdata_future").toBool())
        last->setTextColor("blue");
    }
    _bomitem->expandAll();
  }
}
Example #2
0
bool SGFParser::doParse(const QString &toParseStr)
{
	if (toParseStr.isNull() || toParseStr.isEmpty())
	{
		qWarning("Failed loading from file. Is it empty?");
		return false;
	}
	QString tmp;

	if(!loadedfromfile)
	{
		/* This bit of ugliness is because sgfs are used to duplicate boards as well
		 * as load from file FIXME */
		parseProperty(toParseStr, "CA", tmp);		//codec
		if (!tmp.isEmpty())
			readCodec = QTextCodec::codecForName(tmp.toLatin1().constData());
	}
	
	const MyString *toParse = NULL;

//////TODO	if (static_cast<Codec>(setting->readIntEntry("CODEC")) == codecNone)
/////////		toParse = new MySimpleString(toParseStr);
///////	else
		toParse = new MyString(toParseStr);

	Q_CHECK_PTR(toParse);
	
	int 	pos = 0,
		posVarBegin = 0,
		posVarEnd = 0,
		posNode = 0,
		moves = 0,
		i, x=-1, y=-1;

	int 	a_offset = QChar::fromLatin1('a').unicode() - 1 ;

	unsigned int pointer = 0,
		strLength = toParse->length();
	bool black = true,
		setup = false,
        old_label = false;
	isRoot = true;
	bool remember_root;
	QString unknownProperty;
	State state;
	MarkType markType;
	QString moveStr, commentStr;
	Position *position;
	MoveNum *moveNum;
	QStack<Move*> stack;
	QStack<MoveNum*> movesStack;
	/* FIXME toRemove, et., al., appears unused Remove it */
	QStack<Position*> toRemove;
/*
////TODO	stack.setAutoDelete(false);
	movesStack.setAutoDelete(true);
	toRemove.setAutoDelete(true);
*/
	// Initialises the tree with board size
	parseProperty(toParseStr, "SZ", tmp);
//	Tree *tree = new Tree(tmp.isEmpty() ? 19 : tmp.toInt()) ;// boardHandler->getTree();
	
	state = stateVarBegin;
	
	bool cancel = false;
    //FIXME abort does nothing!!
	
	// qDebug("File length = %d", strLength);
	
    tree->setLoadingSGF(true);
	
	QString sss="";
    do {
		posVarBegin = toParse->find('(', pointer);
		posVarEnd = toParse->find(')', pointer);
		posNode = toParse->find(';', pointer);
		
		pos = minPos(posVarBegin, posVarEnd, posNode);

		// Switch states

		// Node -> VarEnd
		if (state == stateNode && pos == posVarEnd)
			state = stateVarEnd;
		
		// Node -> VarBegin
		if (state == stateNode && pos == posVarBegin)
			state = stateVarBegin;
		
		// VarBegin -> Node
		else if (state == stateVarBegin && pos == posNode)
			state = stateNode;
		
		// VarEnd -> VarBegin
		else if (state == stateVarEnd && pos == posVarBegin)
			state = stateVarBegin;
		
		// qDebug("State after switch = %d", state);
		
		// Do the work
		switch (state)
		{
		case stateVarBegin:
			if (pos != posVarBegin)
			{
				delete toParse;
				return corruptSgf(pos);
			}
			
			// qDebug("Var BEGIN at %d, moves = %d", pos, moves);
			
			stack.push(tree->getCurrent());
			moveNum = new MoveNum;
			moveNum->n = moves;
			movesStack.push(moveNum);
			pointer = pos + 1;
			break;
			
		case stateVarEnd:
			if (pos != posVarEnd)
			{
				delete toParse;
				return corruptSgf(pos);
			}
			
			// qDebug("VAR END");
			
			if (!movesStack.isEmpty() && !stack.isEmpty())
			{
				Move *m = stack.pop();
				Q_CHECK_PTR(m);
				x = movesStack.pop()->n;
				
				// qDebug("Var END at %d, moves = %d, moves from stack = %d", pos, moves, x);
				
				for (i=moves; i > x; i--)
				{
					position = toRemove.pop();
					if (position == NULL)
						continue;
///////////////////			boardHandler->getStoneHandler()->removeStone(position->x, position->y);
//					tree->removeStone(position->x, position->y);
					// qDebug("Removing %d %d from stoneHandler.", position->x, position->y);
				}
				
				moves = x;
 							
				
				tree->setCurrent(m);
			}
			pointer = pos + 1;
			break;
			
		case stateNode:
			if (pos != posNode)
			{
				delete toParse;
				return corruptSgf(pos);
			}
			
			// qDebug("Node at %d", pos);
			commentStr = QString();
			setup = false;
			markType = markNone;
			
			// Create empty node
			remember_root = isRoot;
			if (!isRoot)
			{
/////////////////////		boardHandler->createMoveSGF();
//				qDebug("############### Before creating move ####################");
//				qDebug(toParse->Str.toLatin1().constData());
				//tree->createMoveSGF();
				/* This does happen, why??? FIXME */
//				qDebug("###############                      ####################");
//				qDebug(toParse->Str.toLatin1().constData());
//				qDebug("############### After creating move ####################");
				unknownProperty = QString();
#ifdef FIXME	//why is this a warning? this happens on loading a file with time info
				if (tree->getCurrent()->getTimeinfo())
				qWarning("*** Timeinfo set !!!!");
#endif //FIXME
				//tree->getCurrent()->setTimeinfo(false);
			}
			else
				isRoot = false;
						
			Property prop;
			pos ++;

			do {
				uint tmppos=0;
				pos = toParse->next_nonspace (pos);
				
                if ((tmppos = toParse->isProperty("B",pos)))
				{
					prop = moveBlack;
					pos = tmppos;
					black = true;
				}
                else if ((tmppos = toParse->isProperty("W",pos)))
				{
					prop = moveWhite;
					pos = tmppos;
					black = false;
				}
                else if ((tmppos = toParse->isProperty("N",pos)))
				{
					prop = nodeName;
					pos = tmppos;
				}
                else if ((tmppos = toParse->isProperty("AB",pos)))
				{
					prop = editBlack;
					pos = tmppos;
					setup = true;
					black = true;
				}
                else if ((tmppos = toParse->isProperty("AW",pos)))
				{
					prop = editWhite;
					pos = tmppos;
					setup = true;
					black = false;
				}
                else if ((tmppos = toParse->isProperty("AE",pos)))
				{
					prop = editErase;
					pos = tmppos;
					setup = true;
				}
                else if ((tmppos = toParse->isProperty("TR",pos)))
				{
					prop = editMark;
					markType = markTriangle;
					pos = tmppos;
				}
                else if ((tmppos = toParse->isProperty("CR",pos)))
				{
					prop = editMark;
					markType = markCircle;
					pos = tmppos;
				}
                else if ((tmppos = toParse->isProperty("SQ",pos)))
				{
					prop = editMark;
					markType = markSquare;
					pos = tmppos;
				}
                else if ((tmppos = toParse->isProperty("MA",pos)))
				{
					prop = editMark;
					markType = markCross;
					pos = tmppos;
				}
				// old definition
                else if ((tmppos = toParse->isProperty("M",pos)))
				{
					prop = editMark;
					markType = markCross;
					pos = tmppos;
				}
                else if ((tmppos = toParse->isProperty("LB",pos)))
				{
					prop = editMark;
					markType = markText;
					pos = tmppos;
					old_label = false;
				}
				// Added old L property. This is not SGF4, but many files contain this tag.
                else if ((tmppos = toParse->isProperty("L",pos)))
				{
					prop = editMark;
					markType = markText;
					pos = tmppos;
					old_label = true;
				}
                else if ((tmppos = toParse->isProperty("C",pos)))
				{
					prop = comment;
					pos = tmppos;
				}
                else if ((tmppos = toParse->isProperty("TB",pos)))
				{
					prop = editMark;
					markType = markTerrBlack;
					pos = tmppos;
					black = true;
				}
                else if ((tmppos = toParse->isProperty("TW",pos)))
				{
					prop = editMark;
					markType = markTerrWhite;
					pos = tmppos;
					black = false;
				}
                else if ((tmppos = toParse->isProperty("BL",pos)))
				{
					prop = timeLeft;
					pos = tmppos;
					black = true;
				}
                else if ((tmppos = toParse->isProperty("WL",pos)))
				{
					prop = timeLeft;
					pos = tmppos;
					black = false;
				}
                else if ((tmppos = toParse->isProperty("OB",pos)))
				{
					prop = openMoves;
					pos = tmppos;
					black = true;
				}
                else if ((tmppos = toParse->isProperty("OW",pos)))
				{
					prop = openMoves;
					pos = tmppos;
					black = false;
				}
                else if ((tmppos = toParse->isProperty("PL",pos)))
				{
					prop = nextMove;
					pos = tmppos;
				}
                    else if ((tmppos = toParse->isProperty("RG",pos)))
				{
					prop = unknownProp;
					pos = tmppos;
          				setup = true;
				}
				// Empty node
				else if (toParse->at(pos) == ';' || toParse->at(pos) == '(' || toParse->at(pos) == ')')
				{
					qDebug("Found empty node at %d", pos);
					while (toParse->at(pos).isSpace())
						pos++;
					continue;
				}
				else
				{
					// handle like comment
					prop = unknownProp;
					pos = toParse->next_nonspace (pos);
					//qDebug("SGF: next nonspace (1st):" + QString(toParse->at(pos)) + QString(toParse->at(pos+1)) + QString(toParse->at(pos+2)));
				}
				
				//qDebug("Start do loop : FOUND PROP %d, pos at %d now", prop, pos);
				//qDebug(toParse->getStr());			//causes crash
				// Next is one or more '[xx]'.
				// Only one in a move property, several in a setup propery
				do {
					if (toParse->at(pos) != '[' && prop != unknownProp)
					{
						delete toParse;
						return corruptSgf(pos);
					}
					
					// Empty type
					if (toParse->at(pos+1) == ']')
					{
						// CGoban stores pass as 'B[]' or 'W[]'
						if (prop == moveBlack || prop == moveWhite)
						{
							tree->doPass(true);
							
							// Remember this move for later, to remove from the matrix.
							position = new Position;
							position->x = x;
							position->y = y;
							toRemove.push(position);
							moves ++;
						}
						
						pos += 2;
						continue;
					}
					
					switch (prop)
					{
					case moveBlack:
					case moveWhite:
						// rare case: root contains move or placed stone:
						if (remember_root)
						{
							qDebug("root contains stone -> node created");
							/* Something is screwy here, inconsistencies
							 * in the way SGF's are treated. Like the below:
							 * the whole point of "remember_root", FIXME*/
							tree->addEmptyMove();
							isRoot = false;
							unknownProperty = QString();
#ifdef FIXME	//why is this a warning?
							if (tree->getCurrent()->getTimeinfo())
								qWarning("*** Timeinfo set (2)!!!!");
#endif //FIXME
							//tree->getCurrent()->setTimeinfo(false);
						}
					case editBlack:
					case editWhite:
					case editErase:
					{
						x = toParse->at(pos+1).unicode() - a_offset ;// - 'a';// + 1;
						y = toParse->at(pos+2).unicode() - a_offset ; //- 'a' + 1;

						int x1, y1;
						bool compressed_list;

						// check for compressed lists
						if (toParse->at(pos+3) == ':')
						{
							x1 = toParse->at(pos+4).unicode() -a_offset;// - 'a' + 1;
							y1 = toParse->at(pos+5).unicode() -a_offset;// - 'a' + 1;
							compressed_list = true;
						}
						else
						{
							x1 = x;
							y1 = y;
							compressed_list = false;
						}
/*								
*						TODO Do we nned this when the tree is created from file ?
*						boardHandler->setModeSGF(setup || compressed_list ? modeEdit : modeNormal);
*/
						
						int i, j;
						for (i = x; i <= x1; i++)
							for (j = y; j <= y1; j++)
                            {
                                if (prop == editErase)
								{
									tree->addStoneToCurrentMove(stoneErase, i, j);
								}
								else
								{
									if(setup)
									{
                                        if ((!remember_root) && (stack.top() == tree->getCurrent()))
                                            tree->addEmptyMove(); //if this is first in branch we need to add an empty move

										tree->addStoneToCurrentMove(black ? stoneBlack : stoneWhite, i, j);
									}
									else
                                    {
                                        Move *result = tree->getCurrent()->makeMove(black ? stoneBlack : stoneWhite, i, j);
                                        if (result)
                                            tree->setCurrent(result);
                                    }
								}
								// tree->getCurrent()->getMatrix()->debug();
								//qDebug("ADDING MOVE %s %d/%d", black?"B":"W", x, y);
								
								// Remember this move for later, to remove from the matrix.
								position = new Position;
								position->x = i;
								position->y = j;
								toRemove.push(position);
								moves ++;
							}
												
						if (compressed_list)
							// Advance pos by 7
							pos += 7;
						else
							// Advance pos by 4
							pos += 4;
						break;
					}
						
					case nodeName:
					{
						commentStr = QString();
						bool skip = false;
						
						while (toParse->at(++pos) != ']')
						{
							if (static_cast<unsigned int>(pos) > strLength-1)
							{
								qDebug("SGF: Nodename string ended immediately");
								delete toParse;
								return corruptSgf(pos, "SGF: Nodename string ended immediately");
							}

							// white spaces
							if (toParse->at(pos) == '\\')
							{
								while (toParse->at(pos+1).isSpace() &&
									static_cast<unsigned int>(pos) < strLength-2)
									pos++;
								if (toParse->at(pos).isSpace())
									pos++;

								// case: "../<cr><lf>]"
								if (toParse->at(pos) == ']')
								{
									pos--;
									skip = true;
								}
							}

							// escaped chars: '\', ']', ':'
							if (!(toParse->at(pos) == '\\' &&
								(toParse->at(pos+1) == ']' ||
								 toParse->at(pos+1) == '\\' ||
								 toParse->at(pos+1) == ':')) &&
								 !skip &&
								 // no formatting
								!(toParse->at(pos) == '\n') &&
								!(toParse->at(pos) == '\r'))
								commentStr.append(toParse->at(pos));
						}
						
					 	//qDebug("Node name read: %s", commentStr.toLatin1().constData());
						if (!commentStr.isEmpty())
							// add comment; skip 'C[]'
							tree->getCurrent()->setNodeName(commentStr);
						pos++;
						break;
					}

					case comment:
					{
						commentStr = QString();
						bool skip = false;
						
						while (toParse->at(++pos) != ']' ||
							(toParse->at(pos-1) == '\\' && toParse->at(pos) == ']'))
						{
							if (static_cast<unsigned int>(pos) > strLength-1)
							{
								qDebug("SGF: Comment string ended immediately");
								delete toParse;
								return corruptSgf(pos, "SGF: Comment string ended immediately");
							}

							// white spaces
							if (toParse->at(pos) == '\\')
							{
								while (toParse->at(pos+1).isSpace() &&
									static_cast<unsigned int>(pos) < strLength-2)
									pos++;
								if (toParse->at(pos).isSpace())
									pos++;

								// case: "../<cr><lf>]"
								if (toParse->at(pos) == ']')
								{
									pos--;
									skip = true;
								}
							}

							// escaped chars: '\', ']', ':'
							if (!(toParse->at(pos) == '\\' &&
								(toParse->at(pos+1) == ']' ||
								 toParse->at(pos+1) == '\\' ||
								 toParse->at(pos+1) == ':')) &&
								 !skip)
								commentStr.append(toParse->at(pos));
						}

						//qDebug("Comment read: %s", commentStr.toLatin1().constData());
						if (!commentStr.isEmpty())
						{
							// add comment; skip 'C[]'
							if(readCodec)
								tree->getCurrent()->setComment(readCodec->toUnicode(commentStr.toLatin1().constData()));
							else
								tree->getCurrent()->setComment(commentStr.toLatin1().constData());
						}
						pos ++;
						break;
					}

					case unknownProp:
					{
						// skip if property is known anyway
						bool skip = false;

						// save correct property name (or p.n. + '[')
						commentStr = QString(toParse->at(pos));
						commentStr += toParse->at(tmppos = toParse->next_nonspace (pos + 1));
						pos = tmppos;

						// check if it's really necessary to hold properties
						// maybe they are handled at another position
						if (commentStr == "WR" ||
							commentStr == "BR" ||
							commentStr == "PW" ||
							commentStr == "PB" ||
							commentStr == "SZ" ||
							commentStr == "KM" ||
							commentStr == "HA" ||
							commentStr == "RE" ||
							commentStr == "DT" ||
							commentStr == "PC" ||
							commentStr == "CP" ||
							commentStr == "GN" ||
							commentStr == "OT" ||
							commentStr == "TM" ||
							// now: general options
							commentStr == "GM" ||
							commentStr == "ST" ||
							commentStr == "AP" ||
							commentStr == "FF")
						{
							skip = true;
						}
						sss= toParse->at(pos);
						while (toParse->at(++pos) != ']' ||
							(toParse->at(pos-1) == '\\' && toParse->at(pos) == ']'))
						{
							if (static_cast<unsigned int>(pos) > strLength-1)
							{
								qDebug("SGF: Unknown property ended immediately");
								delete toParse;
								return corruptSgf(pos, "SGF: Unknown property ended immediately");
							}
              						sss= toParse->at(pos);
							if (!skip)
								commentStr.append(toParse->at(pos));
						}

						if (!skip)
							commentStr.append("]");

						// qDebug("Comment read: %s", commentStr.latin1());
						if ((!commentStr.isEmpty()) && (!skip))
						{
							// cumulate unknown properties; skip empty property 'XZ[]'
							unknownProperty += commentStr;
							tree->getCurrent()->setUnknownProperty(unknownProperty);
						}
						pos ++;
            					sss= toParse->at(pos);
						break;
					}

					case editMark:
						// set moveStr for increment labels of old 'L[]' property
						moveStr = "A";
						while (toParse->at(pos) == '[' &&
							static_cast<unsigned int>(pos) < strLength)
						{
							x = toParse->at(pos+1).unicode() -a_offset;// - 'a' + 1;
							y = toParse->at(pos+2).unicode() -a_offset;// - 'a' + 1;
							// qDebug("MARK: %d at %d/%d", markType, x, y);
							pos += 3;
							
							// 'LB' property? Then we need to get the text
							if (markType == markText && !old_label)
							{
								if (toParse->at(pos) != ':')
								{
									delete toParse;
									return corruptSgf(pos);
								}
								moveStr = "";
								while (toParse->at(++pos) != ']' &&
									static_cast<unsigned int>(pos) < strLength)
									moveStr.append(toParse->at(pos));
								// qDebug("LB TEXT = %s", moveStr.latin1());
								// It might me a number mark?
								bool check = false;
								moveStr.toInt(&check);  // Try to convert to Integer
								// treat integers as characters...
								check = false;
								
								if (check)
									tree->getCurrent()->getMatrix()->
									insertMark(x, y, markNumber);  // Worked, its a number
								else
									tree->getCurrent()->getMatrix()->
									insertMark(x, y, markType);    // Nope, its a letter
								tree->getCurrent()->getMatrix()->
										setMarkText(x, y, moveStr);
							
								/*else	//fastload
								{
									if (check)  // Number
										tree->getCurrent()->insertFastLoadMark(x, y, markNumber);
									else        // Text
										tree->getCurrent()->insertFastLoadMark(x, y, markType, moveStr);
								}*/
							}
							else
							{
								int x1, y1;
								bool compressed_list;

								// check for compressed lists
								if (toParse->at(pos) == ':')
								{
									x1 = toParse->at(pos+1).unicode() -a_offset;// - 'a' + 1;
									y1 = toParse->at(pos+2).unicode() -a_offset;// - 'a' + 1;
									compressed_list = true;
								}
								else
								{
									x1 = x;
									y1 = y;
									compressed_list = false;
								}
								
								int i, j;
								for (i = x; i <= x1; i++)
									for (j = y; j <= y1; j++)
									{
										tree->getCurrent()->getMatrix()->insertMark(i, j, markType);
										//else	//fastload
										//	tree->getCurrent()->insertFastLoadMark(i, j, markType);

										// auto increment for old property 'L'
										if (old_label)
										{
											tree->getCurrent()->getMatrix()->
												setMarkText(x, y, moveStr);
											QChar c1 = moveStr[0];
											if (c1 == 'Z')
												moveStr = QString("a");
											else
												moveStr = c1.unicode() + 1;
										}
									}

//								new_node = false;

								if (compressed_list)
									// Advance pos by 3
									pos += 3;

								if((markType == markTerrWhite || markType == markTerrBlack) && !tree->getCurrent()->isTerritoryMarked())
									tree->getCurrent()->setTerritoryMarked();
							}

							//old_label = false;
							pos ++;
							while (toParse->at(pos).isSpace()) pos++;
						}
						break;

					case openMoves:
					{
						QString tmp_mv;
						while (toParse->at(++pos) != ']')
							tmp_mv += toParse->at(pos);
						tree->getCurrent()->setOpenMoves(tmp_mv.toInt());
						pos++;

						if (!tree->getCurrent()->getTimeinfo())
						{
							tree->getCurrent()->setTimeinfo(true);
							tree->getCurrent()->setTimeLeft(0);
						}
						break;
					}

					case timeLeft:
					{
						QString tmp_mv;
						while (toParse->at(++pos) != ']')
							tmp_mv += toParse->at(pos);
						tree->getCurrent()->setTimeLeft(tmp_mv.toFloat());
						pos++;

						if (!tree->getCurrent()->getTimeinfo())
						{
							tree->getCurrent()->setTimeinfo(true);
							tree->getCurrent()->setOpenMoves(0);
						}
						break;
					}

					case nextMove:
						if (toParse->at(++pos) == 'W')
							tree->getCurrent()->setPLinfo(stoneWhite);
						else if (toParse->at(pos) == 'B')
							tree->getCurrent()->setPLinfo(stoneBlack);

						pos += 2;
						break;

					default:
						break;
				}
		
				while (toParse->at(pos).isSpace())
			    		pos++;
        	
				sss= toParse->at(pos);

			} while (setup && toParse->at(pos) == '[');
			
//			tree->getCurrent()->getMatrix()->debug();
//			qDebug("end do loop");
//			qDebug(toParse->getStr());
			
			while (toParse->at(pos).isSpace())
				pos++;

		} while (toParse->at(pos) != ';' && toParse->at(pos) != '(' && toParse->at(pos) != ')' &&    static_cast<unsigned int>(pos) < strLength);
		
		// Advance pointer
		pointer = pos;
	
		break;
	
	default:
		delete toParse;
		return corruptSgf(pointer);
	}
	
	} while (pointer < strLength && pos >= 0);

	tree->setLoadingSGF(false);
	
	delete toParse;
	return !cancel;
}
Example #3
0
QString MessageValidator::validateMessage(QString message, bool* illformed, HTMLTextFormatter* formatter) {

    //    qDebug() << "IMG val0" << message;
    QDomDocument doc("document");
    *illformed = false;

    QString errorMessage;
    int line, column;
    QDomDocument tmpDoc; //used by textformatter

    xmlSource.setData(message);

    if (!doc.setContent(&xmlSource, &xmlReader, &errorMessage, &line, &column)) {
        qDebug() << errorMessage << " " << line << " " << column << message;
        *illformed = true;
        qDebug() << "WARNING: MessageValidator::validateMessage() - illformed message";
        return "illformed message!!!";
    }

    //now DOM tree will be traversed in preorder. 
    QStack<QDomElement> stack; //current element, QStack is used to avoid possible stack overflow in ordinary recursion
    stack.push(doc.documentElement());

    while (!stack.empty()) {
        QDomElement cur = stack.top();
        stack.pop();

        // Traverse through DOM Tree(cur), cut off bad elements/attributes 
        // and format text nodes using textFormatter

        //    qDebug() << QString(4, ' ') << cur.tagName();

        QString parentName = cur.tagName();
        NodeInfo curNI = allowed[parentName];

        //delete disallowed attributes
        for (int i = 0; i < cur.attributes().count(); i++) {
            QString attrName = cur.attributes().item(i).toAttr().name();

            if (!curNI.allowedAttributes.contains(attrName)) {
                //     qDebug() << "VALIDATIN ERR" << "TA" << attrName  << " in " << parentName;
                //   qDebug() << "note allowed attributes are:" << curNI.allowedAttributes;

                cur.attributes().removeNamedItem(attrName);
                i--;
            }
        }

        QDomNodeList children = cur.childNodes();

        for (int i = children.size() - 1; i >= 0; i--) {
            QDomNode node = children.at(i);

            if (node.isElement()) {
                QString childName = node.toElement().tagName();

                if (childName == "a") { // always show hyperlink destination
                    QString href = node.toElement().attribute("href");
                    node.appendChild(doc.createTextNode(" [ " + href + " ]"));
                }

                if (childName == "style") { //NOTE: this action is not XHTML-IM compliant! (css rules should be displayed, but it's stupid)
                    cur.removeChild(node);
                }
                else if (childName == "img") { //disabling images until they are whitelisted

                    QString href = node.toElement().attribute("src");

                    QDomElement newElement = doc.createElement("a");
                    newElement.setAttribute("class", "psi_disabled_image");
                    newElement.setAttribute("href", "javascript:psi_addToWhiteList('" + href + "')");
                    newElement.appendChild(doc.createTextNode("[ click here to display: " + href + " ]"));

                    cur.replaceChild(newElement, node);
                }
                else if (!curNI.allowedTags.contains(childName)) {//is subElement valid here?

                    qDebug() << "VALIDATIN ERR" << "TS" << childName << " in " << parentName;
                    qDebug() << "note allowed subElements are:" << curNI.allowedTags;

                    //append bad node's children (they will be validated in next loop iteration)
                    int j = 0;
                    while (node.hasChildNodes()) {
                        cur.insertBefore(node.firstChild(), node);
                        j++;
                    }

                    i = i + j; //j nodes were inserted

                    //delete bad node
                    cur.removeChild(node);
                }
                else {
                    stack.push(node.toElement());
                }
            }
            else if (node.isText() && !node.isCDATASection()) {
                if (!curNI.canHaveText) {
                    cur.removeChild(node);
                }
                else { //format text
                    QString formattedText = "<tmp>" + formatter->format(Qt::escape(node.toText().data()), cur) + "</tmp>";
                    //NOTE: we don't need to escape quotes, and we want this code be more reusable/decoupled, 
                    //NOTE: so we use Qt::escape() instead of TextUtil::escape()
                   
                    xmlSource.setData(formattedText);
                    tmpDoc.setContent(&xmlSource, &xmlReader);
                   
                    QDomNode tmpElement = tmpDoc.firstChild();
                    while (tmpElement.hasChildNodes()) { //append <tmp>'s children. They won't be validated
                        cur.insertBefore(tmpElement.firstChild(), node);
                    }
                    
                    cur.removeChild(node);
                }
            }
        }//foreach child
    } //stack/dfs

//    qDebug() << "IMG MV:" << doc.toString(0);
    return doc.toString(0);
}
Example #4
0
static void parse( Translator *tor )
{
    QString text;
    QString com;
    QString extracomment;

    yyCh = getChar();

    yyTok = getToken();
    while ( yyTok != Tok_Eof ) {
        switch ( yyTok ) {
        case Tok_class:
            yyTok = getToken();
            if(yyTok == Tok_Ident) {
                yyScope.push(new Scope(yyIdent, Scope::Clazz, yyLineNo));
            }
            else {
                yyMsg() << qPrintable(LU::tr("'class' must be followed by a class name.\n"));
                break;
            }
            while (!match(Tok_LeftBrace)) {
                yyTok = getToken();
            }
            break;

        case Tok_tr:
            yyTok = getToken();
            if ( match(Tok_LeftParen) && matchString(text) ) {
                com.clear();
                bool plural = false;

                if ( match(Tok_RightParen) ) {
                    // no comment
                } else if (match(Tok_Comma) && matchStringOrNull(com)) {   //comment
                    if ( match(Tok_RightParen)) {
                        // ok,
                    } else if (match(Tok_Comma)) {
                        plural = true;
                    }
                }
                if (!text.isEmpty())
                    recordMessage(tor, context(), text, com, extracomment, plural);
            }
            break;
        case Tok_translate:
            {
                QString contextOverride;
                yyTok = getToken();
                if ( match(Tok_LeftParen) &&
                     matchString(contextOverride) &&
                     match(Tok_Comma) &&
                     matchString(text) ) {

                    com.clear();
                    bool plural = false;
                    if (!match(Tok_RightParen)) {
                        // look for comment
                        if ( match(Tok_Comma) && matchStringOrNull(com)) {
                            if (!match(Tok_RightParen)) {
                                if (match(Tok_Comma) && matchExpression() && match(Tok_RightParen)) {
                                    plural = true;
                                } else {
                                    break;
                                }
                            }
                        } else {
                            break;
                        }
                    }
                    if (!text.isEmpty())
                        recordMessage(tor, contextOverride, text, com, extracomment, plural);
                }
            }
            break;

        case Tok_Ident:
            yyTok = getToken();
            break;

        case Tok_Comment:
            if (yyComment.startsWith(QLatin1Char(':'))) {
                yyComment.remove(0, 1);
                extracomment.append(yyComment);
            }
            yyTok = getToken();
            break;

        case Tok_RightBrace:
            if ( yyScope.isEmpty() ) {
                yyMsg() << qPrintable(LU::tr("Excess closing brace.\n"));
            }
            else
                delete (yyScope.pop());
            extracomment.clear();
            yyTok = getToken();
            break;

         case Tok_LeftBrace:
            yyScope.push(new Scope(QString(), Scope::Other, yyLineNo));
            yyTok = getToken();
            break;

        case Tok_Semicolon:
            extracomment.clear();
            yyTok = getToken();
            break;

        case Tok_Package:
            yyTok = getToken();
            while(!match(Tok_Semicolon)) {
                switch(yyTok) {
                    case Tok_Ident:
                        yyPackage.append(yyIdent);
                        break;
                    case Tok_Dot:
                        yyPackage.append(QLatin1String("."));
                        break;
                    default:
                         yyMsg() << qPrintable(LU::tr("'package' must be followed by package name.\n"));
                         break;
                }
                yyTok = getToken();
            }
            break;

        default:
            yyTok = getToken();
        }
    }

    if ( !yyScope.isEmpty() )
        yyMsg(yyScope.top()->line) << qPrintable(LU::tr("Unbalanced opening brace.\n"));
    else if ( yyParenDepth != 0 )
        yyMsg(yyParenLineNo) << qPrintable(LU::tr("Unbalanced opening parenthesis.\n"));
}
Example #5
0
void Loader::load()
{
    QFile in(QLatin1String("tree.xml"));

    /* LoadingModel::m_result will be null, signalling failure. */
    if(!in.open(QIODevice::ReadOnly))
        return;

    QXmlStreamReader reader(&in);
    while(!reader.atEnd())
    {
        reader.readNext();

        switch(reader.tokenType())
        {
            case QXmlStreamReader::StartDocument:
            /* Fallthrough. */
            case QXmlStreamReader::StartElement:
            {
                QXmlName name;
                if(reader.tokenType() == QXmlStreamReader::StartElement)
                {
                    name = QXmlName(m_namePool,
                                    reader.name().toString(),
                                    reader.namespaceUri().toString(),
                                    reader.prefix().toString());
                }
                /* Else, the name is null. */

                LoadingModel::Node *const tmp = new LoadingModel::Node(reader.tokenType() == QXmlStreamReader::StartElement
                                                                       ? QXmlNodeModelIndex::Element
                                                                       : QXmlNodeModelIndex::Document,
                                                                       m_parentStack.top(),
                                                                       QString(),
                                                                       name);
                m_result.append(tmp);

                if(m_currentNode)
                {
                    if(m_currentNode->parent == m_parentStack.top())
                        m_currentNode->followingSibling = tmp;
                }

                const QXmlStreamAttributes attributes(reader.attributes());
                const int len = attributes.count();

                for(int i = 0; i < len; ++i)
                {
                    const QXmlStreamAttribute &attr = attributes.at(i);
                    const LoadingModel::Node *const a = new LoadingModel::Node(QXmlNodeModelIndex::Attribute,
                                                                               m_parentStack.top(),
                                                                               attr.value().toString(),
                                                                               QXmlName(m_namePool,
                                                                                       attr.name().toString(),
                                                                                       attr.namespaceUri().toString(),
                                                                                       attr.prefix().toString()));
                    /* We add it also to m_result such that compareOrder() is correct
                     * for attributes. m_result owns a. */
                    tmp->attributes.append(a);
                    m_result.append(a);
                }

                adjustSiblings(tmp);
                m_parentStack.push(m_currentNode);
                break;
            }
            case QXmlStreamReader::EndDocument:
            /* Fallthrough. */
            case QXmlStreamReader::EndElement:
            {
                m_currentNode->followingSibling = 0;
                m_currentNode = m_parentStack.pop();

                if(reader.tokenType() == QXmlStreamReader::EndDocument)
                    const_cast<LoadingModel::Node *>(m_result.first())->followingSibling = 0;

                break;
            }
            case QXmlStreamReader::Characters:
            {
                LoadingModel::Node *const tmp = new LoadingModel::Node(QXmlNodeModelIndex::Text, m_parentStack.top(), reader.text().toString());
                m_result.append(tmp);
                adjustSiblings(tmp);
                break;
            }
            case QXmlStreamReader::ProcessingInstruction:
            {
                LoadingModel::Node *const tmp = new LoadingModel::Node(QXmlNodeModelIndex::ProcessingInstruction,
                                                                       m_parentStack.top(),
                                                                       reader.processingInstructionData().toString(),
                                                                       QXmlName(m_namePool, reader.processingInstructionTarget().toString()));
                m_result.append(tmp);
                adjustSiblings(tmp);
                break;
            }
            case QXmlStreamReader::Comment:
            {
                LoadingModel::Node *const tmp = new LoadingModel::Node(QXmlNodeModelIndex::Comment, m_parentStack.top(), reader.text().toString());
                m_result.append(tmp);
                adjustSiblings(tmp);
                break;
            }
            case QXmlStreamReader::DTD:
                qFatal("%s: QXmlStreamReader::DTD token is not supported", Q_FUNC_INFO);
                break;
            case QXmlStreamReader::EntityReference:
                qFatal("%s: QXmlStreamReader::EntityReference token is not supported", Q_FUNC_INFO);
                break;
            case QXmlStreamReader::NoToken:
            /* Fallthrough. */
            case QXmlStreamReader::Invalid:
            {
                qWarning("%s", qPrintable(reader.errorString()));
                m_result.clear();
                return;
            }
        }
    }

    if(reader.hasError())
    {
        qWarning("%s", qPrintable(reader.errorString()));
        m_result.clear();
    }
}
TableFieldBinaryTreeEvalNode* TableFieldBinaryTreeEvalNode::buildTree(QList<TableFieldEvalNode *>& list, QObject *parent)
{
  if (list.isEmpty())
  {
      return nullptr;
  }

  // Build a new list that is surrounded with parenthesis.
  QList<TableFieldEvalNode *> safeList;
  TableFieldEvalNode leftParenEvalNode(TableFieldEvalNode::L_PAREN);
  TableFieldEvalNode rightParenEvalNode(TableFieldEvalNode::R_PAREN);
  TableFieldBinaryTreeEvalNode* headNode = new TableFieldBinaryTreeEvalNode(parent);

  safeList.append(&leftParenEvalNode);
  safeList.append(list);
  safeList.append(&rightParenEvalNode);

  bool isError = false;
  QStack<TableFieldBinaryTreeEvalNode*> values;
  QStack<TableFieldBinaryTreeEvalNode*> operators;

  QListIterator<TableFieldEvalNode*> i(safeList);
  while (i.hasNext() && !isError)
  {
      TableFieldEvalNode* eNode = i.next();
      if (eNode == nullptr)
      {
        qDebug(qPrintable(tr("Cannot build a tree from null nodes.")));
        isError = true;
      }
      else if (eNode->isValue())
      {
          // Push value nodes on the value stack.
          TableFieldBinaryTreeEvalNode* bNode = new TableFieldBinaryTreeEvalNode(headNode);
          bNode->setNode(eNode->clone(bNode));
          values.push(bNode);
      }
      else if (eNode->isLeftParen())
      {
          // Push left parenthesis onto the operator stack.
          // Will be removed when a right parenthesis is found.
          TableFieldBinaryTreeEvalNode* bNode = new TableFieldBinaryTreeEvalNode(headNode);
          bNode->setNode(eNode->clone(bNode));
          operators.push(bNode);
      }
      else if (eNode->isRightParen())
      {
          // Found a right parenthesis.
          // Process all operators until a left parenthesis is found then get rid of it.
          while (!isError && !operators.isEmpty() && !operators.top()->isLeftParen())
        {
          isError = processOneTreeLevel(values, operators);
        }
        if (!isError)
        {
          if (operators.isEmpty())
          {
            qDebug(qPrintable(tr("Have a ')' without a '('")));
            isError = true;
          }
          else
          {
            // Dispose of the open parenthesis.
            TableFieldBinaryTreeEvalNode* opNode = operators.pop();
            delete opNode;
          }
        }
      }
      else if (eNode->isNoType())
      {
          qDebug(qPrintable(tr("Cannot build a tree from raw nodes with no type")));
          isError = true;
      }
      else
      {
          // Found an operator.
          // Process all operators whose priority / precidence is the same or greater than this one.
          // So, after reading "a OR b OR", you know you can set "a OR b", but you don't know yet if you can
          // process the second OR.
        while (!isError && !operators.isEmpty() && !operators.top()->isLeftParen() && operators.top()->nodePriority() >= eNode->nodePriority())
        {
            isError = processOneTreeLevel(values, operators);
        }
        if (!isError)
        {
            // No error, so push the operator onto the operator stack.
            TableFieldBinaryTreeEvalNode* bNode = new TableFieldBinaryTreeEvalNode(headNode);
            bNode->setNode(eNode->clone(bNode));
            operators.push(bNode);
        }
      }
  }

  if (!isError)
  {
    if (!operators.isEmpty())
    {
      isError = true;
      qDebug(qPrintable(tr("Unprocessed Operators left in the stack after processing")));
    }
    else if (values.size() != 1)
    {
      isError = true;
      qDebug(qPrintable(tr("There should be only one value left after processing, not %1").arg(values.size())));
    }
    else
    {
        // tree parent node should already be null.
        // Perform a shallow copy of the top node into the head node.
        TableFieldBinaryTreeEvalNode* topNode = values.top();

        // Clone the node so that the parent / owner is properly set.
        headNode->m_node = topNode->m_node->clone(headNode);
        for (int i=0; i<topNode->m_children.size(); ++i)
        {
            headNode->addChild(topNode->m_children.at(i));
        }

        delete topNode;
        return headNode;
    }
  }
  if (isError)
  {
      // All of the created nodes are a child of the head node.
      delete headNode;
  }
  return nullptr;
}
Example #7
0
TypeParser::Info TypeParser::parse(const QString &str) {
    Scanner scanner(str);

    Info info;
    QStack<Info *> stack;
    stack.push(&info);

    bool colon_prefix = false;
    bool in_array = false;
    QString array;

    Scanner::Token tok = scanner.nextToken();
    while (tok != Scanner::NoToken) {

        switch (tok) {

            case Scanner::StarToken:
                ++stack.top()->indirections;
                break;

            case Scanner::AmpersandToken:
                stack.top()->is_reference = true;
                break;

            case Scanner::LessThanToken:
                stack.top()->template_instantiations << Info();
                stack.push(&stack.top()->template_instantiations.last());
                break;

            case Scanner::CommaToken:
                stack.pop();
                stack.top()->template_instantiations << Info();
                stack.push(&stack.top()->template_instantiations.last());
                break;

            case Scanner::GreaterThanToken:
                stack.pop();
                break;

            case Scanner::ColonToken:
                colon_prefix = true;
                break;

            case Scanner::ConstToken:
                stack.top()->is_constant = true;
                break;

            case Scanner::OpenParenToken: // function pointers not supported
            case Scanner::CloseParenToken: {
                Info i;
                i.is_busted = true;
                return i;
            }

            case Scanner::Identifier:
                parseIdentifier(scanner, stack, array, in_array, colon_prefix);
                break;

            case Scanner::SquareBegin:
                in_array = true;
                break;

            case Scanner::SquareEnd:
                in_array = false;
                stack.top()->arrays += array;
                break;

            default:
                break;
        }

        tok = scanner.nextToken();
    }

    return info;
}
Example #8
0
void TraceLoader::parseTrace()
{
    QList<ApiTraceFrame*> frames;
    ApiTraceFrame *currentFrame = 0;
    int frameCount = 0;
    QStack<ApiTraceCall*> groups;
    QVector<ApiTraceCall*> topLevelItems;
    QVector<ApiTraceCall*> allCalls;
    quint64 binaryDataSize = 0;

    int lastPercentReport = 0;

    trace::Call *call = m_parser.parse_call();
    while (call) {
        //std::cout << *call;
        if (!currentFrame) {
            currentFrame = new ApiTraceFrame();
            currentFrame->number = frameCount;
            ++frameCount;
        }
        ApiTraceCall *apiCall =
            apiCallFromTraceCall(call, m_helpHash, currentFrame, groups.isEmpty() ? 0 : groups.top(), this);
        allCalls.append(apiCall);
        if (groups.count() == 0) {
            topLevelItems.append(apiCall);
        }
        if (call->flags & trace::CALL_FLAG_MARKER_PUSH) {
            groups.push(apiCall);
        } else if (call->flags & trace::CALL_FLAG_MARKER_POP) {
            groups.top()->finishedAddingChildren();
            groups.pop();
        }
        if (!groups.isEmpty()) {
            groups.top()->addChild(apiCall);
        }
        if (apiCall->hasBinaryData()) {
            QByteArray data =
                apiCall->arguments()[apiCall->binaryDataIndex()].toByteArray();
            binaryDataSize += data.size();
        }
        if (call->flags & trace::CALL_FLAG_END_FRAME) {
            allCalls.squeeze();
            topLevelItems.squeeze();
            if (topLevelItems.count() == allCalls.count()) {
                currentFrame->setCalls(allCalls, allCalls, binaryDataSize);
            } else {
                currentFrame->setCalls(topLevelItems, allCalls, binaryDataSize);
            }
            allCalls.clear();
            groups.clear();
            topLevelItems.clear();
            frames.append(currentFrame);
            currentFrame = 0;
            binaryDataSize = 0;
            if (frames.count() >= FRAMES_TO_CACHE) {
                emit framesLoaded(frames);
                frames.clear();
            }
            if (m_parser.percentRead() - lastPercentReport >= 5) {
                emit parsed(m_parser.percentRead());
                lastPercentReport = m_parser.percentRead();
            }
        }
        delete call;
        call = m_parser.parse_call();
    }

    //last frames won't have markers
    //  it's just a bunch of Delete calls for every object
    //  after the last SwapBuffers
    if (currentFrame) {
        allCalls.squeeze();
        if (topLevelItems.count() == allCalls.count()) {
            currentFrame->setCalls(allCalls, allCalls, binaryDataSize);
        } else {
            currentFrame->setCalls(topLevelItems, allCalls, binaryDataSize);
        }
        frames.append(currentFrame);
        currentFrame = 0;
    }
    if (frames.count()) {
        emit framesLoaded(frames);
    }
}
Example #9
0
void AccelTree::copyNodeTo(const QXmlNodeModelIndex &node,
                           QAbstractXmlReceiver *const receiver,
                           const NodeCopySettings &settings) const
{
    /* This code piece can be seen as a customized version of
     * QAbstractXmlReceiver::item/sendAsNode(). */
    Q_ASSERT(receiver);
    Q_ASSERT(!node.isNull());

    typedef QHash<QXmlName::PrefixCode, QXmlName::NamespaceCode> Binding;
    QStack<Binding> outputted;

    switch(node.kind())
    {
        case QXmlNodeModelIndex::Element:
        {
            outputted.push(Binding());

            /* Add the namespace for our element name. */
            const QXmlName elementName(node.name());

            receiver->startElement(elementName);

            if(!settings.testFlag(InheritNamespaces))
                receiver->namespaceBinding(QXmlName(StandardNamespaces::StopNamespaceInheritance, 0,
                                                    StandardPrefixes::StopNamespaceInheritance));

            if(settings.testFlag(PreserveNamespaces))
                node.sendNamespaces(receiver);
            else
            {
                /* Find the namespaces that we actually use and add them to outputted. These are drawn
                 * from the element name, and the node's attributes. */
                outputted.top().insert(elementName.prefix(), elementName.namespaceURI());

                const QXmlNodeModelIndex::Iterator::Ptr attributes(iterate(node, QXmlNodeModelIndex::AxisAttribute));
                QXmlNodeModelIndex attr(attributes->next());

                while(!attr.isNull())
                {
                    const QXmlName &attrName = attr.name();
                    outputted.top().insert(attrName.prefix(), attrName.namespaceURI());
                    attr = attributes->next();
                }

                Binding::const_iterator it(outputted.top().constBegin());
                const Binding::const_iterator end(outputted.top().constEnd());

                for(; it != end; ++it)
                    receiver->namespaceBinding(QXmlName(it.value(), 0, it.key()));
            }

            /* Send the attributes of the element. */
            {
                QXmlNodeModelIndex::Iterator::Ptr attributes(node.iterate(QXmlNodeModelIndex::AxisAttribute));
                QXmlNodeModelIndex attribute(attributes->next());

                while(!attribute.isNull())
                {
                    const QString &v = attribute.stringValue();
                    receiver->attribute(attribute.name(), QStringRef(&v));
                    attribute = attributes->next();
                }
            }

            /* Send the children of the element. */
            copyChildren(node, receiver, settings);

            receiver->endElement();
            outputted.pop();
            break;
        }
        case QXmlNodeModelIndex::Document:
        {
            /* We need to intercept and grab the elements of the document node, such
             * that we preserve/inherit preference applies to them. */
            receiver->startDocument();
            copyChildren(node, receiver, settings);
            receiver->endDocument();
            break;
        }
        default:
            receiver->item(node);
    }

}
Example #10
0
bool RCCResourceLibrary::interpretResourceFile(QIODevice *inputDevice,
    const QString &fname, QString currentPath, bool ignoreErrors)
{
    Q_ASSERT(m_errorDevice);
    const QChar slash = QLatin1Char('/');
    if (!currentPath.isEmpty() && !currentPath.endsWith(slash))
        currentPath += slash;

    QXmlStreamReader reader(inputDevice);
    QStack<RCCXmlTag> tokens;

    QString prefix;
    QLocale::Language language = QLocale::c().language();
    QLocale::Country country = QLocale::c().country();
    QString alias;
    int compressLevel = m_compressLevel;
    int compressThreshold = m_compressThreshold;

    while (!reader.atEnd()) {
        QXmlStreamReader::TokenType t = reader.readNext();
        switch (t) {
        case QXmlStreamReader::StartElement:
            if (reader.name() == m_strings.TAG_RCC) {
                if (!tokens.isEmpty())
                    reader.raiseError(QLatin1String("expected <RCC> tag"));
                else
                    tokens.push(RccTag);
            } else if (reader.name() == m_strings.TAG_RESOURCE) {
                if (tokens.isEmpty() || tokens.top() != RccTag) {
                    reader.raiseError(QLatin1String("unexpected <RESOURCE> tag"));
                } else {
                    tokens.push(ResourceTag);

                    QXmlStreamAttributes attributes = reader.attributes();
                    language = QLocale::c().language();
                    country = QLocale::c().country();

                    if (attributes.hasAttribute(m_strings.ATTRIBUTE_LANG)) {
                        QString attribute = attributes.value(m_strings.ATTRIBUTE_LANG).toString();
                        QLocale lang = QLocale(attribute);
                        language = lang.language();
                        if (2 == attribute.length()) {
                            // Language only
                            country = QLocale::AnyCountry;
                        } else {
                            country = lang.country();
                        }
                    }

                    prefix.clear();
                    if (attributes.hasAttribute(m_strings.ATTRIBUTE_PREFIX))
                        prefix = attributes.value(m_strings.ATTRIBUTE_PREFIX).toString();
                    if (!prefix.startsWith(slash))
                        prefix.prepend(slash);
                    if (!prefix.endsWith(slash))
                        prefix += slash;
                }
            } else if (reader.name() == m_strings.TAG_FILE) {
                if (tokens.isEmpty() || tokens.top() != ResourceTag) {
                    reader.raiseError(QLatin1String("unexpected <FILE> tag"));
                } else {
                    tokens.push(FileTag);

                    QXmlStreamAttributes attributes = reader.attributes();
                    alias.clear();
                    if (attributes.hasAttribute(m_strings.ATTRIBUTE_ALIAS))
                        alias = attributes.value(m_strings.ATTRIBUTE_ALIAS).toString();

                    compressLevel = m_compressLevel;
                    if (attributes.hasAttribute(m_strings.ATTRIBUTE_COMPRESS))
                        compressLevel = attributes.value(m_strings.ATTRIBUTE_COMPRESS).toString().toInt();

                    compressThreshold = m_compressThreshold;
                    if (attributes.hasAttribute(m_strings.ATTRIBUTE_THRESHOLD))
                        compressThreshold = attributes.value(m_strings.ATTRIBUTE_THRESHOLD).toString().toInt();

                    // Special case for -no-compress. Overrides all other settings.
                    if (m_compressLevel == -2)
                        compressLevel = 0;
                }
            } else {
                reader.raiseError(QString(QLatin1String("unexpected tag: %1")).arg(reader.name().toString()));
            }
            break;

        case QXmlStreamReader::EndElement:
            if (reader.name() == m_strings.TAG_RCC) {
                if (!tokens.isEmpty() && tokens.top() == RccTag)
                    tokens.pop();
                else
                    reader.raiseError(QLatin1String("unexpected closing tag"));
            } else if (reader.name() == m_strings.TAG_RESOURCE) {
                if (!tokens.isEmpty() && tokens.top() == ResourceTag)
                    tokens.pop();
                else
                    reader.raiseError(QLatin1String("unexpected closing tag"));
            } else if (reader.name() == m_strings.TAG_FILE) {
                if (!tokens.isEmpty() && tokens.top() == FileTag)
                    tokens.pop();
                else
                    reader.raiseError(QLatin1String("unexpected closing tag"));
            }
            break;

        case QXmlStreamReader::Characters:
            if (reader.isWhitespace())
                break;
            if (tokens.isEmpty() || tokens.top() != FileTag) {
                reader.raiseError(QLatin1String("unexpected text"));
            } else {
                QString fileName = reader.text().toString();
                if (fileName.isEmpty()) {
                    const QString msg = QString::fromLatin1("RCC: Warning: Null node in XML of '%1'\n").arg(fname);
                    m_errorDevice->write(msg.toUtf8());
                }

                if (alias.isNull())
                    alias = fileName;

                alias = QDir::cleanPath(alias);
                while (alias.startsWith(QLatin1String("../")))
                    alias.remove(0, 3);
                alias = QDir::cleanPath(m_resourceRoot) + prefix + alias;

                QString absFileName = fileName;
                if (QDir::isRelativePath(absFileName))
                    absFileName.prepend(currentPath);
                QFileInfo file(absFileName);
                if (!file.exists()) {
                    m_failedResources.push_back(absFileName);
                    const QString msg = QString::fromLatin1("RCC: Error in '%1': Cannot find file '%2'\n").arg(fname).arg(fileName);
                    m_errorDevice->write(msg.toUtf8());
                    if (ignoreErrors)
                        continue;
                    else
                        return false;
                } else if (file.isFile()) {
                    const bool arc =
                        addFile(alias,
                                RCCFileInfo(alias.section(slash, -1),
                                            file,
                                            language,
                                            country,
                                            RCCFileInfo::NoFlags,
                                            compressLevel,
                                            compressThreshold)
                                );
                    if (!arc)
                        m_failedResources.push_back(absFileName);
                } else {
                    QDir dir;
                    if (file.isDir()) {
                        dir.setPath(file.filePath());
                    } else {
                        dir.setPath(file.path());
                        dir.setNameFilters(QStringList(file.fileName()));
                        if (alias.endsWith(file.fileName()))
                            alias = alias.left(alias.length()-file.fileName().length());
                    }
                    if (!alias.endsWith(slash))
                        alias += slash;
                    QDirIterator it(dir, QDirIterator::FollowSymlinks|QDirIterator::Subdirectories);
                    while (it.hasNext()) {
                        it.next();
                        QFileInfo child(it.fileInfo());
                        if (child.fileName() != QLatin1String(".") && child.fileName() != QLatin1String("..")) {
                            const bool arc =
                                addFile(alias + child.fileName(),
                                        RCCFileInfo(child.fileName(),
                                                    child,
                                                    language,
                                                    country,
                                                    RCCFileInfo::NoFlags,
                                                    compressLevel,
                                                    compressThreshold)
                                        );
                            if (!arc)
                                m_failedResources.push_back(child.fileName());
                        }
                    }
                }
            }
            break;

        default:
            break;
        }
    }

    if (reader.hasError()) {
        if (ignoreErrors)
            return true;
        int errorLine = reader.lineNumber();
        int errorColumn = reader.columnNumber();
        QString errorMessage = reader.errorString();
        QString msg = QString::fromLatin1("RCC Parse Error: '%1' Line: %2 Column: %3 [%4]\n").arg(fname).arg(errorLine).arg(errorColumn).arg(errorMessage);
        m_errorDevice->write(msg.toUtf8());
        return false;
    }

    if (m_root == 0) {
        const QString msg = QString::fromUtf8("RCC: Warning: No resources in '%1'.\n").arg(fname);
        m_errorDevice->write(msg.toUtf8());
        if (!ignoreErrors && m_format == Binary) {
            // create dummy entry, otherwise loading with QResource will crash
            m_root = new RCCFileInfo(QString(), QFileInfo(),
                    QLocale::C, QLocale::AnyCountry, RCCFileInfo::Directory);
        }
    }

    return true;
}
Example #11
0
void dspIndentedWhereUsed::sFillList()
{
  _bomitem->clear();

  if (_item->isValid())
  {
    q.prepare("SELECT indentedWhereUsed(:item_id) AS workset_id;");
    q.bindValue(":item_id", _item->id());
    q.exec();
    if (q.first())
    {
      int worksetid = q.value("workset_id").toInt();

      QString sql( "SELECT bomwork_level, bomwork_id, item_id, bomwork_parent_id,"
		           "       bomworkitemsequence(bomwork_id) as seqord, "
                   "       bomwork_seqnumber, item_number, uom_name,"
                   "       (item_descrip1 || ' ' || item_descrip2) AS itemdescription,"
                   "       formatQtyPer(bomwork_qtyper) AS qtyper,"
                   "       formatScrap(bomwork_scrap) AS scrap,"
                   "       formatDate(bomwork_effective, 'Always') AS effective,"
                   "       formatDate(bomwork_expires, 'Never') AS expires "
                   "FROM bomwork, item, uom "
                   "WHERE ( (bomwork_item_id=item_id)"
                   " AND (item_inv_uom_id=uom_id)"
                   " AND (bomwork_set_id=:bomwork_set_id)" );

      if (!_showExpired->isChecked())
        sql += " AND (bomwork_expires > CURRENT_DATE)";

      if (!_showFuture->isChecked())
        sql += " AND (bomwork_effective <= CURRENT_DATE)";

      sql += ") "
             "ORDER BY seqord;";

      q.prepare(sql);
      q.bindValue(":bomwork_set_id", worksetid);
      q.exec();

      QStack<XTreeWidgetItem*> parent;
      XTreeWidgetItem *last = 0;
      int level = 0;
      while(q.next())
      {
        // If the level this item is on is lower than the last level we just did then we need
        // to pop the stack a number of times till we are equal.
        while(q.value("bomwork_level").toInt() < level)
        {
          level--;
          last = parent.pop();
        }

        // If the level this item is on is higher than the last level we need to push the last
        // item onto the stack a number of times till we are equal. (Should only ever be 1.)
        while(q.value("bomwork_level").toInt() > level)
        {
          level++;
          parent.push(last);
          last = 0;
        }

        // If there is an item in the stack use that as the parameter to the new xlistviewitem
        // otherwise we'll just use the xlistview _layout
        if(!parent.isEmpty() && parent.top())
          last = new XTreeWidgetItem(parent.top(), last, q.value("bomwork_id").toInt(), q.value("item_id").toInt(),
                             q.value("bomwork_seqnumber"), q.value("item_number"),
                             q.value("itemdescription"), q.value("uom_name"),
                             q.value("qtyper"), q.value("scrap"),
                             q.value("effective"), q.value("expires") );
        else
          last = new XTreeWidgetItem(_bomitem, last, q.value("bomwork_id").toInt(), q.value("item_id").toInt(),
                             q.value("bomwork_seqnumber"), q.value("item_number"),
                             q.value("itemdescription"), q.value("uom_name"),
                             q.value("qtyper"), q.value("scrap"),
                             q.value("effective"), q.value("expires") );

      }
      _bomitem->expandAll();

      q.prepare("SELECT deleteBOMWorkset(:workset_id) AS result;");
      q.bindValue(":bomwork_set_id", worksetid);
      q.exec();
    }
  }
}
Example #12
0
void OwncloudPropagator::start(const SyncFileItemVector &items)
{
    Q_ASSERT(std::is_sorted(items.begin(), items.end()));

    /* This builds all the jobs needed for the propagation.
     * Each directory is a PropagateDirectory job, which contains the files in it.
     * In order to do that we loop over the items. (which are sorted by destination)
     * When we enter a directory, we can create the directory job and push it on the stack. */

    _rootJob.reset(new PropagateDirectory(this));
    QStack<QPair<QString /* directory name */, PropagateDirectory * /* job */>> directories;
    directories.push(qMakePair(QString(), _rootJob.data()));
    QVector<PropagatorJob *> directoriesToRemove;
    QString removedDirectory;
    foreach (const SyncFileItemPtr &item, items) {
        if (!removedDirectory.isEmpty() && item->_file.startsWith(removedDirectory)) {
            // this is an item in a directory which is going to be removed.
            PropagateDirectory *delDirJob = qobject_cast<PropagateDirectory *>(directoriesToRemove.first());

            if (item->_instruction == CSYNC_INSTRUCTION_REMOVE) {
                // already taken care of. (by the removal of the parent directory)

                // increase the number of subjobs that would be there.
                if (delDirJob) {
                    delDirJob->increaseAffectedCount();
                }
                continue;
            } else if (item->isDirectory()
                && (item->_instruction == CSYNC_INSTRUCTION_NEW
                       || item->_instruction == CSYNC_INSTRUCTION_TYPE_CHANGE)) {
                // create a new directory within a deleted directory? That can happen if the directory
                // etag was not fetched properly on the previous sync because the sync was aborted
                // while uploading this directory (which is now removed).  We can ignore it.
                if (delDirJob) {
                    delDirJob->increaseAffectedCount();
                }
                continue;
            } else if (item->_instruction == CSYNC_INSTRUCTION_IGNORE) {
                continue;
            } else if (item->_instruction == CSYNC_INSTRUCTION_RENAME) {
                // all is good, the rename will be executed before the directory deletion
            } else {
                qCWarning(lcPropagator) << "WARNING:  Job within a removed directory?  This should not happen!"
                                        << item->_file << item->_instruction;
            }
        }

        while (!item->destination().startsWith(directories.top().first)) {
            directories.pop();
        }

        if (item->isDirectory()) {
            PropagateDirectory *dir = new PropagateDirectory(this, item);

            if (item->_instruction == CSYNC_INSTRUCTION_TYPE_CHANGE
                && item->_direction == SyncFileItem::Up) {
                // Skip all potential uploads to the new folder.
                // Processing them now leads to problems with permissions:
                // checkForPermissions() has already run and used the permissions
                // of the file we're about to delete to decide whether uploading
                // to the new dir is ok...
                foreach (const SyncFileItemPtr &item2, items) {
                    if (item2->destination().startsWith(item->destination() + "/")) {
                        item2->_instruction = CSYNC_INSTRUCTION_NONE;
                        _anotherSyncNeeded = true;
                    }
                }
            }

            if (item->_instruction == CSYNC_INSTRUCTION_REMOVE) {
                // We do the removal of directories at the end, because there might be moves from
                // these directories that will happen later.
                directoriesToRemove.prepend(dir);
                removedDirectory = item->_file + "/";

                // We should not update the etag of parent directories of the removed directory
                // since it would be done before the actual remove (issue #1845)
                // NOTE: Currently this means that we don't update those etag at all in this sync,
                //       but it should not be a problem, they will be updated in the next sync.
                for (int i = 0; i < directories.size(); ++i) {
                    if (directories[i].second->_item->_instruction == CSYNC_INSTRUCTION_UPDATE_METADATA)
                        directories[i].second->_item->_instruction = CSYNC_INSTRUCTION_NONE;
                }
            } else {
                PropagateDirectory *currentDirJob = directories.top().second;
                currentDirJob->appendJob(dir);
            }
            directories.push(qMakePair(item->destination() + "/", dir));
        } else {
Example #13
0
QVector<ApiTraceCall*>
TraceLoader::fetchFrameContents(ApiTraceFrame *currentFrame)
{
    Q_ASSERT(currentFrame);

    if (currentFrame->isLoaded()) {
        return currentFrame->calls();
    }

    if (m_parser.supportsOffsets()) {
        unsigned frameIdx = currentFrame->number;
        int numOfCalls = numberOfCallsInFrame(frameIdx);

        if (numOfCalls) {
            quint64 binaryDataSize = 0;
            QStack<ApiTraceCall*> groups;
            QVector<ApiTraceCall*> topLevelItems;
            QVector<ApiTraceCall*> allCalls(numOfCalls);
            const FrameBookmark &frameBookmark = m_frameBookmarks[frameIdx];

            m_parser.setBookmark(frameBookmark.start);

            trace::Call *call;
            int parsedCalls = 0;
            while ((call = m_parser.parse_call())) {
                ApiTraceCall *apiCall =
                    apiCallFromTraceCall(call, m_helpHash,
                                         currentFrame, groups.isEmpty() ? 0 : groups.top(), this);
                Q_ASSERT(apiCall);
                Q_ASSERT(parsedCalls < allCalls.size());
                allCalls[parsedCalls++] = apiCall;
                if (groups.count() == 0) {
                    topLevelItems.append(apiCall);
                } else {
                    groups.top()->addChild(apiCall);
                }
                if (call->flags & trace::CALL_FLAG_MARKER_PUSH) {
                    groups.push(apiCall);
                } else if (call->flags & trace::CALL_FLAG_MARKER_POP) {
                    if (groups.count()) {
                        groups.top()->finishedAddingChildren();
                        groups.pop();
                    }
                }
                if (apiCall->hasBinaryData()) {
                    QByteArray data =
                        apiCall->arguments()[
                            apiCall->binaryDataIndex()].toByteArray();
                    binaryDataSize += data.size();
                }

                delete call;

                if (apiCall->flags() & trace::CALL_FLAG_END_FRAME) {
                    break;
                }

            }
            // There can be fewer parsed calls when call in different
            // threads cross the frame boundary
            Q_ASSERT(parsedCalls <= numOfCalls);
            Q_ASSERT(parsedCalls <= allCalls.size());
            allCalls.resize(parsedCalls);
            allCalls.squeeze();

            Q_ASSERT(parsedCalls <= currentFrame->numChildrenToLoad());
            if (topLevelItems.count() == allCalls.count()) {
                emit frameContentsLoaded(currentFrame, allCalls,
                                         allCalls, binaryDataSize);
            } else {
                emit frameContentsLoaded(currentFrame, topLevelItems,
                                         allCalls, binaryDataSize);
            }
            return allCalls;
        }
    }
    return QVector<ApiTraceCall*>();
}
Example #14
0
void Highlighter::iterateThroughRules(const QString &text,
                                      const int length,
                                      ProgressData *progress,
                                      const bool childRule,
                                      const QList<QSharedPointer<Rule> > &rules)
{
    typedef QList<QSharedPointer<Rule> >::const_iterator RuleIterator;

    bool contextChanged = false;
    bool atLeastOneMatch = false;

    RuleIterator it = rules.begin();
    RuleIterator endIt = rules.end();
    while (it != endIt && progress->offset() < length) {
        int startOffset = progress->offset();
        const QSharedPointer<Rule> &rule = *it;
        if (rule->matchSucceed(text, length, progress)) {
            atLeastOneMatch = true;

            if (!m_indentationBasedFolding) {
                if (!rule->beginRegion().isEmpty()) {
                    blockData(currentBlockUserData())->m_foldingRegions.push(rule->beginRegion());
                    ++m_regionDepth;
                    if (progress->isOpeningBraceMatchAtFirstNonSpace())
                        ++blockData(currentBlockUserData())->m_foldingIndentDelta;
                }
                if (!rule->endRegion().isEmpty()) {
                    QStack<QString> *currentRegions =
                        &blockData(currentBlockUserData())->m_foldingRegions;
                    if (!currentRegions->isEmpty() && rule->endRegion() == currentRegions->top()) {
                        currentRegions->pop();
                        --m_regionDepth;
                        if (progress->isClosingBraceMatchAtNonEnd())
                            --blockData(currentBlockUserData())->m_foldingIndentDelta;
                    }
                }
                progress->clearBracesMatches();
            }

            if (progress->isWillContinueLine()) {
                createWillContinueBlock();
                progress->setWillContinueLine(false);
            } else {
                if (rule->hasChildren())
                    iterateThroughRules(text, length, progress, true, rule->children());

                if (!rule->context().isEmpty() && contextChangeRequired(rule->context())) {
                    m_currentCaptures = progress->captures();
                    changeContext(rule->context(), rule->definition());
                    contextChanged = true;
                }
            }

            // Format is not applied to child rules directly (but relative to the offset of their
            // parent) nor to look ahead rules.
            if (!childRule && !rule->isLookAhead()) {
                if (rule->itemData().isEmpty())
                    applyFormat(startOffset, progress->offset() - startOffset,
                                m_currentContext->itemData(), m_currentContext->definition());
                else
                    applyFormat(startOffset, progress->offset() - startOffset, rule->itemData(),
                                rule->definition());
            }

            // When there is a match of one child rule the others should be skipped. Otherwise
            // the highlighting would be incorret in a case like 9ULLLULLLUULLULLUL, for example.
            if (contextChanged || childRule) {
                break;
            } else {
                it = rules.begin();
                continue;
            }
        }
        ++it;
    }

    if (!childRule && !atLeastOneMatch) {
        if (m_currentContext->isFallthrough()) {
            handleContextChange(m_currentContext->fallthroughContext(),
                                m_currentContext->definition());
            iterateThroughRules(text, length, progress, false, m_currentContext->rules());
        } else {
            applyFormat(progress->offset(), 1, m_currentContext->itemData(),
                        m_currentContext->definition());
            if (progress->isOnlySpacesSoFar() && !text.at(progress->offset()).isSpace())
                progress->setOnlySpacesSoFar(false);
            progress->incrementOffset();
        }
    }
}
void QmlProfilerEventsModelProxy::loadData(qint64 rangeStart, qint64 rangeEnd)
{
    clear();

    qint64 qmlTime = 0;
    qint64 lastEndTime = 0;
    QHash <int, QVector<qint64> > durations;

    const bool checkRanges = (rangeStart != -1) && (rangeEnd != -1);

    const QVector<QmlProfilerDataModel::QmlEventData> &eventList
            = d->modelManager->qmlModel()->getEvents();
    const QVector<QmlProfilerDataModel::QmlEventTypeData> &typesList
            = d->modelManager->qmlModel()->getEventTypes();

    // used by binding loop detection
    QStack<const QmlProfilerDataModel::QmlEventData*> callStack;
    callStack.push(0); // artificial root

    for (int i = 0; i < eventList.size(); ++i) {
        const QmlProfilerDataModel::QmlEventData *event = &eventList[i];
        const QmlProfilerDataModel::QmlEventTypeData *type = &typesList[event->typeIndex];

        if (!d->acceptedTypes.contains(type->rangeType))
            continue;

        if (checkRanges) {
            if ((event->startTime + event->duration < rangeStart)
                    || (event->startTime > rangeEnd))
                continue;
        }

        // update stats
        QmlEventStats *stats = &d->data[event->typeIndex];

        stats->duration += event->duration;
        if (event->duration < stats->minTime)
            stats->minTime = event->duration;
        if (event->duration > stats->maxTime)
            stats->maxTime = event->duration;
        stats->calls++;

        // for median computing
        durations[event->typeIndex].append(event->duration);

        // qml time computation
        if (event->startTime > lastEndTime) { // assume parent event if starts before last end
            qmlTime += event->duration;
            lastEndTime = event->startTime + event->duration;
        }


        //
        // binding loop detection
        //
        const QmlProfilerDataModel::QmlEventData *potentialParent = callStack.top();
        while (potentialParent
               && !(potentialParent->startTime + potentialParent->duration > event->startTime)) {
            callStack.pop();
            potentialParent = callStack.top();
        }

        // check whether event is already in stack
        for (int ii = 1; ii < callStack.size(); ++ii) {
            if (callStack.at(ii)->typeIndex == event->typeIndex) {
                d->eventsInBindingLoop.insert(event->typeIndex);
                break;
            }
        }

        callStack.push(event);

        d->modelManager->modelProxyCountUpdated(d->modelId, i, eventList.count()*2);
    }

    // post-process: calc mean time, median time, percentoftime
    int i = d->data.size();
    int total = i * 2;

    for (QHash<int, QmlEventStats>::iterator it = d->data.begin(); it != d->data.end(); ++it) {
        QmlEventStats* stats = &it.value();
        if (stats->calls > 0)
            stats->timePerCall = stats->duration / (double)stats->calls;

        QVector<qint64> eventDurations = durations[it.key()];
        if (!eventDurations.isEmpty()) {
            Utils::sort(eventDurations);
            stats->medianTime = eventDurations.at(eventDurations.count()/2);
        }

        stats->percentOfTime = stats->duration * 100.0 / qmlTime;
        d->modelManager->modelProxyCountUpdated(d->modelId, i++, total);
    }

    // set binding loop flag
    foreach (int typeIndex, d->eventsInBindingLoop)
        d->data[typeIndex].isBindingLoop = true;

    // insert root event
    QmlEventStats rootEvent;
    rootEvent.duration = rootEvent.minTime = rootEvent.maxTime = rootEvent.timePerCall
                       = rootEvent.medianTime = qmlTime + 1;
    rootEvent.calls = 1;
    rootEvent.percentOfTime = 100.0;

    d->data.insert(-1, rootEvent);

    d->modelManager->modelProxyCountUpdated(d->modelId, 1, 1);
    emit dataAvailable();
}
Example #16
0
/*!
    \internal
*/
void QDirIteratorPrivate::advance()
{
    // Store the current entry
    if (!fileEngineIterators.isEmpty())
        currentFilePath = fileEngineIterators.top()->currentFilePath();

    // Advance to the next entry
    if (followNextDir) {
        // Start by navigating into the current directory.
        followNextDir = false;

        QAbstractFileEngineIterator *it = fileEngineIterators.top();

        QString subDir = it->currentFilePath();
#ifdef Q_OS_WIN
        if (fileInfo.isSymLink())
            subDir = fileInfo.canonicalFilePath();
#endif
        pushSubDirectory(subDir, it->nameFilters(), it->filters());
    }

    if (fileEngineIterators.isEmpty())
        done = true;

    bool foundValidEntry = false;
    while (!fileEngineIterators.isEmpty()) {
        QAbstractFileEngineIterator *it = fileEngineIterators.top();

        // Find the next valid iterator that matches the filters.
        foundValidEntry = false;
        while (it->hasNext()) {
            it->next();
            if (matchesFilters(it)) {
                foundValidEntry = true;
                break;
            }
        }

        if (!foundValidEntry) {
            // If this iterator is done, pop and delete it, and continue
            // iteration on the parent. Otherwise break, we're done.
            if (!fileEngineIterators.isEmpty()) {
                delete it;
                it = fileEngineIterators.pop();
                continue;
            }
            break;
        }

        fileInfo = it->currentFileInfo();

        // If we're doing flat iteration, we're done.
        if (!(iteratorFlags & QDirIterator::Subdirectories))
            break;

        // Subdirectory iteration.
        QString filePath = fileInfo.filePath();

        // Never follow . and ..
        if (fileInfo.fileName() == QLatin1String(".") || fileInfo.fileName() == QLatin1String(".."))
            break;

        // Never follow non-directory entries
        if (!fileInfo.isDir())
            break;
      
        // Check symlinks
        if (fileInfo.isSymLink() && !(iteratorFlags & QDirIterator::FollowSymlinks)) {
            // Follow symlinks only if FollowSymlinks was passed
            break;
        }

        // Stop link loops
        if (visitedLinks.contains(fileInfo.canonicalFilePath()))
            break;

        // Signal that we want to follow this entry.
        followNextDir = true;
        break;
    }

    if (!foundValidEntry)
        done = true;
}
Example #17
0
TypeParser::Info TypeParser::parse(const QString &str)
{
    Scanner scanner(str);

    Info info;
    QStack<Info *> stack;
    stack.push(&info);

    bool colon_prefix = false;
    bool in_array = false;
    QString array;

    Scanner::Token tok = scanner.nextToken();
    while (tok != Scanner::NoToken) {

//         switch (tok) {
//         case Scanner::StarToken: printf(" - *\n"); break;
//         case Scanner::AmpersandToken: printf(" - &\n"); break;
//         case Scanner::LessThanToken: printf(" - <\n"); break;
//         case Scanner::GreaterThanToken: printf(" - >\n"); break;
//         case Scanner::ColonToken: printf(" - ::\n"); break;
//         case Scanner::CommaToken: printf(" - ,\n"); break;
//         case Scanner::ConstToken: printf(" - const\n"); break;
//         case Scanner::SquareBegin: printf(" - [\n"); break;
//         case Scanner::SquareEnd: printf(" - ]\n"); break;
//         case Scanner::Identifier: printf(" - '%s'\n", qPrintable(scanner.identifier())); break;
//         default:
//             break;
//         }

        switch (tok) {

        case Scanner::StarToken:
            ++stack.top()->indirections;
            break;

        case Scanner::AmpersandToken:
            stack.top()->is_reference = true;
            break;

        case Scanner::LessThanToken:
            stack.top()->template_instantiations << Info();
            stack.push(&stack.top()->template_instantiations.last());
            break;

        case Scanner::CommaToken:
            stack.pop();
            stack.top()->template_instantiations << Info();
            stack.push(&stack.top()->template_instantiations.last());
            break;

        case Scanner::GreaterThanToken:
            stack.pop();
            break;

        case Scanner::ColonToken:
            colon_prefix = true;
            break;

        case Scanner::ConstToken:
            stack.top()->is_constant = true;
            break;

        case Scanner::OpenParenToken: // function pointers not supported
        case Scanner::CloseParenToken: {
            Info i;
            i.is_busted = true;
            return i;
        }


        case Scanner::Identifier:
            if (in_array) {
                array = scanner.identifier();
            } else if (colon_prefix || stack.top()->qualified_name.isEmpty()) {
                stack.top()->qualified_name << scanner.identifier();
                colon_prefix = false;
            } else {
                stack.top()->qualified_name.last().append(" " + scanner.identifier());
            }
            break;

        case Scanner::SquareBegin:
            in_array = true;
            break;

        case Scanner::SquareEnd:
            in_array = false;
            stack.top()->arrays += array;
            break;


        default:
            break;
        }

        tok = scanner.nextToken();
    }

    return info;
}