PB_DS_CLASS_T_DEC
inline bool
PB_DS_CLASS_C_DEC::
erase_imp(const_key_reference r_key, true_type)
{
  const comp_hash pos_hash_pair = ranged_probe_fn_base::operator()(r_key);
  size_type i;
  resize_base::notify_erase_search_start();
  for (i = 0; i < m_num_e; ++i)
    {
      const size_type pos = ranged_probe_fn_base::operator()(r_key, pos_hash_pair.second, i);

      entry* const p_e = m_entries + pos;
      switch(p_e->m_stat)
        {
        case empty_entry_status:
	  {
	    resize_base::notify_erase_search_end();
	    _GLIBCXX_DEBUG_ONLY(map_debug_base::check_key_does_not_exist(
								    r_key));
	    return false;
	  }
	  break;
        case valid_entry_status:
	  if (hash_eq_fn_base::operator()(PB_DS_V2F(p_e->m_value), p_e->m_hash,
					  r_key, pos_hash_pair.second))
            {
	      resize_base::notify_erase_search_end();
	      erase_entry(p_e);
	      do_resize_if_needed_no_throw();
	      return true;
            }
	  break;
        case erased_entry_status:
	  break;
        default:
	  _GLIBCXX_DEBUG_ASSERT(0);
        };

      resize_base::notify_erase_search_collision();
    }
  resize_base::notify_erase_search_end();
  return false;
}
PB_DS_CLASS_T_DEC
inline bool
PB_DS_CLASS_C_DEC::
erase_imp(key_const_reference r_key,  false_type)
{
  PB_DS_ASSERT_VALID((*this))
  size_type hash = ranged_probe_fn_base::operator()(r_key);
  size_type i;
  resize_base::notify_erase_search_start();

  for (i = 0; i < m_num_e; ++i)
    {
      const size_type pos = ranged_probe_fn_base::operator()(r_key,  hash, i);
      entry* const p_e = m_entries + pos;
      switch(p_e->m_stat)
        {
        case empty_entry_status:
	  {
	    resize_base::notify_erase_search_end();
	    PB_DS_CHECK_KEY_DOES_NOT_EXIST(r_key)
	    return false;
	  }
	  break;
        case valid_entry_status:
	  if (hash_eq_fn_base::operator()(PB_DS_V2F(p_e->m_value), r_key))
            {
	      resize_base::notify_erase_search_end();
	      erase_entry(p_e);
	      do_resize_if_needed_no_throw();
	      return true;
            }
	  break;
        case erased_entry_status:
	  break;
        default:
	  _GLIBCXX_DEBUG_ASSERT(0);
        };
      resize_base::notify_erase_search_collision();
    }
  resize_base::notify_erase_search_end();
  return false;
}
Example #3
0
int
parameter_flashfs_write(flash_file_token_t token, uint8_t *buffer, size_t buf_size)
{
	int rv = -ENXIO;

	if (sector_map) {

		rv = 0;

		/* Calculate the total space needed */

		size_t total_size = buf_size + sizeof(flash_entry_header_t);
		size_t alignment = sizeof(h_magic_t) - 1;
		size_t  size_adjust = ((total_size + alignment) & ~alignment) - total_size;
		total_size += size_adjust;

		/* Is this and existing entry */

		flash_entry_header_t *pf = find_entry(token);

		if (!pf) {

			/* No Entry exists for this token so find a place for it */

			pf = find_free(total_size);

			/* No Space */

			if (pf == 0) {
				return -ENOSPC;
			}

		} else {

			/* Do we have space after the entry in the sector for the update */

			sector_descriptor_t *current_sector = check_free_space_in_sector(pf,
							      total_size);


			if (current_sector == 0) {

				/* Mark the last entry erased */

				/* todo:consider a 2 stage erase or write before erase and do a fs check
				 * at start up
				 */

				rv = erase_entry(pf);

				if (rv < 0) {
					return rv;
				}

				/* We had space and marked the last entry erased so use the  Next Free */

				pf = next_entry(pf);

			} else {

				/*
				 * We did not have space in the current sector so select the next sector
				 */

				current_sector = get_next_sector_descriptor(current_sector);

				/* Will the data fit */

				if (current_sector->size < total_size) {
					return -ENOSPC;
				}

				/* Mark the last entry erased */

				/* todo:consider a 2 stage erase or write before erase and do a fs check
				 * at start up
				 */

				rv = erase_entry(pf);

				if (rv < 0) {
					return rv;
				}

				pf = (flash_entry_header_t *) current_sector->address;
			}

			if (!blank_check(pf, total_size)) {
				rv = erase_sector(current_sector, pf);
			}
		}

		flash_entry_header_t *pn = (flash_entry_header_t *)(buffer - sizeof(flash_entry_header_t));
		pn->magic = MagicSig;
		pn->file_token.t = token.t;
		pn->flag = ValidEntry + size_adjust;
		pn->size = total_size;

		for (size_t a = 0; a < size_adjust; a++) {
			buffer[buf_size + a] = (uint8_t)BlankSig;
		}

		pn->crc = crc32(entry_crc_start(pn), entry_crc_length(pn));
		rv = up_progmem_write((size_t) pf, pn, pn->size);
		int system_bytes = (sizeof(flash_entry_header_t) + size_adjust);

		if (rv >= system_bytes) {
			rv -= system_bytes;
		}
	}

	return rv;
}