Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

thunderbolt: Add tb_property_copy_dir()

This function takes a deep copy of the properties. We need this in order
to support more dynamic properties per XDomain connection as required by
the USB4 inter-domain service spec.

Signed-off-by: Mika Westerberg <mika.westerberg@linux.intel.com>

+72
+71
drivers/thunderbolt/property.c
··· 502 502 } 503 503 504 504 /** 505 + * tb_property_copy_dir() - Take a deep copy of directory 506 + * @dir: Directory to copy 507 + * 508 + * This function takes a deep copy of @dir and returns back the copy. In 509 + * case of error returns %NULL. The resulting directory needs to be 510 + * released by calling tb_property_free_dir(). 511 + */ 512 + struct tb_property_dir *tb_property_copy_dir(const struct tb_property_dir *dir) 513 + { 514 + struct tb_property *property, *p = NULL; 515 + struct tb_property_dir *d; 516 + 517 + if (!dir) 518 + return NULL; 519 + 520 + d = tb_property_create_dir(dir->uuid); 521 + if (!d) 522 + return NULL; 523 + 524 + list_for_each_entry(property, &dir->properties, list) { 525 + struct tb_property *p; 526 + 527 + p = tb_property_alloc(property->key, property->type); 528 + if (!p) 529 + goto err_free; 530 + 531 + p->length = property->length; 532 + 533 + switch (property->type) { 534 + case TB_PROPERTY_TYPE_DIRECTORY: 535 + p->value.dir = tb_property_copy_dir(property->value.dir); 536 + if (!p->value.dir) 537 + goto err_free; 538 + break; 539 + 540 + case TB_PROPERTY_TYPE_DATA: 541 + p->value.data = kmemdup(property->value.data, 542 + property->length * 4, 543 + GFP_KERNEL); 544 + if (!p->value.data) 545 + goto err_free; 546 + break; 547 + 548 + case TB_PROPERTY_TYPE_TEXT: 549 + p->value.text = kzalloc(p->length * 4, GFP_KERNEL); 550 + if (!p->value.text) 551 + goto err_free; 552 + strcpy(p->value.text, property->value.text); 553 + break; 554 + 555 + case TB_PROPERTY_TYPE_VALUE: 556 + p->value.immediate = property->value.immediate; 557 + break; 558 + 559 + default: 560 + break; 561 + } 562 + 563 + list_add_tail(&p->list, &d->properties); 564 + } 565 + 566 + return d; 567 + 568 + err_free: 569 + kfree(p); 570 + tb_property_free_dir(d); 571 + 572 + return NULL; 573 + } 574 + 575 + /** 505 576 * tb_property_add_immediate() - Add immediate property to directory 506 577 * @parent: Directory to add the property 507 578 * @key: Key for the property
+1
include/linux/thunderbolt.h
··· 146 146 size_t block_len); 147 147 ssize_t tb_property_format_dir(const struct tb_property_dir *dir, u32 *block, 148 148 size_t block_len); 149 + struct tb_property_dir *tb_property_copy_dir(const struct tb_property_dir *dir); 149 150 struct tb_property_dir *tb_property_create_dir(const uuid_t *uuid); 150 151 void tb_property_free_dir(struct tb_property_dir *dir); 151 152 int tb_property_add_immediate(struct tb_property_dir *parent, const char *key,